ocamlweb-1.41/0000755000246300004300000000000013422556306012567 5ustar filliatrvalsocamlweb-1.41/test/0000755000246300004300000000000013422556306013546 5ustar filliatrvalsocamlweb-1.41/ocaml-parser/0000755000246300004300000000000013422556307015155 5ustar filliatrvalsocamlweb-1.41/ocaml-parser/misc.mli0000755000246300004300000001112113422556306016611 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Miscellaneous useful types and functions *) val fatal_error: string -> 'a exception Fatal_error val try_finally : (unit -> 'a) -> (unit -> unit) -> 'a;; val map_end: ('a -> 'b) -> 'a list -> 'b list -> 'b list (* [map_end f l t] is [map f l @ t], just more efficient. *) val map_left_right: ('a -> 'b) -> 'a list -> 'b list (* Like [List.map], with guaranteed left-to-right evaluation order *) val for_all2: ('a -> 'b -> bool) -> 'a list -> 'b list -> bool (* Same as [List.for_all] but for a binary predicate. In addition, this [for_all2] never fails: given two lists with different lengths, it returns false. *) val replicate_list: 'a -> int -> 'a list (* [replicate_list elem n] is the list with [n] elements all identical to [elem]. *) val list_remove: 'a -> 'a list -> 'a list (* [list_remove x l] returns a copy of [l] with the first element equal to [x] removed. *) val split_last: 'a list -> 'a list * 'a (* Return the last element and the other elements of the given list. *) val samelist: ('a -> 'a -> bool) -> 'a list -> 'a list -> bool (* Like [List.for_all2] but returns [false] if the two lists have different length. *) val may: ('a -> unit) -> 'a option -> unit val may_map: ('a -> 'b) -> 'a option -> 'b option val find_in_path: string list -> string -> string (* Search a file in a list of directories. *) val find_in_path_uncap: string list -> string -> string (* Same, but search also for uncapitalized name, i.e. if name is Foo.ml, allow /path/Foo.ml and /path/foo.ml to match. *) val remove_file: string -> unit (* Delete the given file if it exists. Never raise an error. *) val expand_directory: string -> string -> string (* [expand_directory alt file] eventually expands a [+] at the beginning of file into [alt] (an alternate root directory) *) val create_hashtable: int -> ('a * 'b) list -> ('a, 'b) Hashtbl.t (* Create a hashtable of the given size and fills it with the given bindings. *) val copy_file: in_channel -> out_channel -> unit (* [copy_file ic oc] reads the contents of file [ic] and copies them to [oc]. It stops when encountering EOF on [ic]. *) val copy_file_chunk: in_channel -> out_channel -> int -> unit (* [copy_file_chunk ic oc n] reads [n] bytes from [ic] and copies them to [oc]. It raises [End_of_file] when encountering EOF on [ic]. *) val log2: int -> int (* [log2 n] returns [s] such that [n = 1 lsl s] if [n] is a power of 2*) val align: int -> int -> int (* [align n a] rounds [n] upwards to a multiple of [a] (a power of 2). *) val no_overflow_add: int -> int -> bool (* [no_overflow_add n1 n2] returns [true] if the computation of [n1 + n2] does not overflow. *) val no_overflow_sub: int -> int -> bool (* [no_overflow_add n1 n2] returns [true] if the computation of [n1 - n2] does not overflow. *) val no_overflow_lsl: int -> bool (* [no_overflow_add n] returns [true] if the computation of [n lsl 1] does not overflow. *) val chop_extension_if_any: string -> string (* Like Filename.chop_extension but returns the initial file name if it has no extension *) val search_substring: string -> string -> int -> int (* [search_substring pat str start] returns the position of the first occurrence of string [pat] in string [str]. Search starts at offset [start] in [str]. Raise [Not_found] if [pat] does not occur. *) val rev_split_words: string -> string list (* [rev_split_words s] splits [s] in blank-separated words, and return the list of words in reverse order. *) ocamlweb-1.41/ocaml-parser/misc.ml0000755000246300004300000001177613422556306016460 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Errors *) exception Fatal_error let fatal_error msg = prerr_string ">> Fatal error: "; prerr_endline msg; raise Fatal_error (* Exceptions *) let try_finally f1 f2 = try let result = f1 () in f2 (); result with x -> f2 (); raise x ;; (* List functions *) let rec map_end f l1 l2 = match l1 with [] -> l2 | hd::tl -> f hd :: map_end f tl l2 let rec map_left_right f = function [] -> [] | hd::tl -> let res = f hd in res :: map_left_right f tl let rec for_all2 pred l1 l2 = match (l1, l2) with ([], []) -> true | (hd1::tl1, hd2::tl2) -> pred hd1 hd2 && for_all2 pred tl1 tl2 | (_, _) -> false let rec replicate_list elem n = if n <= 0 then [] else elem :: replicate_list elem (n-1) let rec list_remove x = function [] -> [] | hd :: tl -> if hd = x then tl else hd :: list_remove x tl let rec split_last = function [] -> assert false | [x] -> ([], x) | hd :: tl -> let (lst, last) = split_last tl in (hd :: lst, last) let rec samelist pred l1 l2 = match (l1, l2) with | ([], []) -> true | (hd1 :: tl1, hd2 :: tl2) -> pred hd1 hd2 && samelist pred tl1 tl2 | (_, _) -> false (* Options *) let may f = function Some x -> f x | None -> () let may_map f = function Some x -> Some (f x) | None -> None (* File functions *) let find_in_path path name = if not (Filename.is_implicit name) then if Sys.file_exists name then name else raise Not_found else begin let rec try_dir = function [] -> raise Not_found | dir::rem -> let fullname = Filename.concat dir name in if Sys.file_exists fullname then fullname else try_dir rem in try_dir path end let find_in_path_uncap path name = let uname = String.uncapitalize name in let rec try_dir = function [] -> raise Not_found | dir::rem -> let fullname = Filename.concat dir name and ufullname = Filename.concat dir uname in if Sys.file_exists ufullname then ufullname else if Sys.file_exists fullname then fullname else try_dir rem in try_dir path let remove_file filename = try Sys.remove filename with Sys_error msg -> () (* Expand a -I option: if it starts with +, make it relative to the standard library directory *) let expand_directory alt s = if String.length s > 0 && s.[0] = '+' then Filename.concat alt (String.sub s 1 (String.length s - 1)) else s (* Hashtable functions *) let create_hashtable size init = let tbl = Hashtbl.create size in List.iter (fun (key, data) -> Hashtbl.add tbl key data) init; tbl (* File copy *) let copy_file ic oc = let buff = String.create 0x1000 in let rec copy () = let n = input ic buff 0 0x1000 in if n = 0 then () else (output oc buff 0 n; copy()) in copy() let copy_file_chunk ic oc len = let buff = String.create 0x1000 in let rec copy n = if n <= 0 then () else begin let r = input ic buff 0 (min n 0x1000) in if r = 0 then raise End_of_file else (output oc buff 0 r; copy(n-r)) end in copy len (* Integer operations *) let rec log2 n = if n <= 1 then 0 else 1 + log2(n asr 1) let align n a = if n >= 0 then (n + a - 1) land (-a) else n land (-a) let no_overflow_add a b = (a lxor b) lor (a lxor (lnot (a+b))) < 0 let no_overflow_sub a b = (a lxor (lnot b)) lor (b lxor (a-b)) < 0 let no_overflow_lsl a = min_int asr 1 <= a && a <= max_int asr 1 (* String operations *) let chop_extension_if_any fname = try Filename.chop_extension fname with Invalid_argument _ -> fname let search_substring pat str start = let rec search i j = if j >= String.length pat then i else if i + j >= String.length str then raise Not_found else if str.[i + j] = pat.[j] then search i (j+1) else search (i+1) 0 in search start 0 let rev_split_words s = let rec split1 res i = if i >= String.length s then res else begin match s.[i] with ' ' | '\t' | '\r' | '\n' -> split1 res (i+1) | _ -> split2 res i (i+1) end and split2 res i j = if j >= String.length s then String.sub s i (j-i) :: res else begin match s.[j] with ' ' | '\t' | '\r' | '\n' -> split1 (String.sub s i (j-i) :: res) (j+1) | _ -> split2 res i (j+1) end in split1 [] 0 ocamlweb-1.41/ocaml-parser/clflags.ml0000755000246300004300000000162013422556306017123 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Command-line parameters *) let fast = ref false (* -unsafe *) ocamlweb-1.41/ocaml-parser/terminfo.mli0000755000246300004300000000210713422556306017505 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Basic interface to the terminfo database *) type status = | Uninitialised | Bad_term | Good_term of int (* number of lines of the terminal *) ;; val setup : out_channel -> status val backup : int -> unit val standout : bool -> unit val resume : int -> unit ocamlweb-1.41/ocaml-parser/terminfo.ml0000755000246300004300000000241513422556306017336 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Basic interface to the terminfo database *) type status = | Uninitialised | Bad_term | Good_term of int ;; (* external setup : out_channel -> status = "caml_terminfo_setup";; *) (* external backup : int -> unit = "caml_terminfo_backup";; *) (* external standout : bool -> unit = "caml_terminfo_standout";; *) (* external resume : int -> unit = "caml_terminfo_resume";; *) let setup _c = Bad_term let backup _n = () let standout _b = () let resume _n = () ocamlweb-1.41/ocaml-parser/warnings.mli0000755000246300004300000000324113422556306017512 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Pierre Weis && Damien Doligez, INRIA Rocquencourt *) (* *) (* Copyright 1998 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) open Format type t = (* A is all *) | Comment of string (* C *) | Deprecated (* D *) | Fragile_pat of string (* E *) | Partial_application (* F *) | Labels_omitted (* L *) | Method_override of string list (* M *) | Partial_match of string (* P *) | Statement_type (* S *) | Unused_match (* U *) | Unused_pat (* U *) | Hide_instance_variable of string (* V *) | Other of string (* X *) ;; val parse_options : bool -> string -> unit;; val is_active : t -> bool;; val is_error : t -> bool;; val print : formatter -> t -> int;; (* returns the number of newlines in the printed string *) exception Errors of int;; val check_fatal : unit -> unit;; ocamlweb-1.41/ocaml-parser/warnings.ml0000755000246300004300000001156013422556306017344 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Pierre Weis && Damien Doligez, INRIA Rocquencourt *) (* *) (* Copyright 1998 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Please keep them in alphabetical order *) type t = (* A is all *) | Comment of string (* C *) | Deprecated (* D *) | Fragile_pat of string (* E *) | Partial_application (* F *) | Labels_omitted (* L *) | Method_override of string list (* M *) | Partial_match of string (* P *) | Statement_type (* S *) | Unused_match (* U *) | Unused_pat (* U *) | Hide_instance_variable of string (* V *) | Other of string (* X *) ;; let letter = function (* 'a' is all *) | Comment _ -> 'c' | Deprecated -> 'd' | Fragile_pat _ -> 'e' | Partial_application -> 'f' | Labels_omitted -> 'l' | Method_override _ -> 'm' | Partial_match _ -> 'p' | Statement_type -> 's' | Unused_match|Unused_pat -> 'u' | Hide_instance_variable _ -> 'v' | Other _ -> 'x' ;; let check c = try ignore (String.index "acdeflmpsuvxACDEFLMPSUVX" c) with _ -> raise (Arg.Bad (Printf.sprintf "unknown warning option %c" c)) ;; let active = Array.make 26 true;; let error = Array.make 26 false;; let translate c = check c; if c >= 'A' && c <= 'Z' then (Char.code c - Char.code 'A', true) else (Char.code c - Char.code 'a', false) ;; let is_active x = let (n, _) = translate (letter x) in active.(n) ;; let is_error x = let (n, _) = translate (letter x) in error.(n) ;; let parse_options iserr s = let flags = if iserr then error else active in for i = 0 to String.length s - 1 do if s.[i] = 'A' then Array.fill flags 0 (Array.length flags) true else if s.[i] = 'a' then Array.fill flags 0 (Array.length flags) false else begin let (n, fl) = translate s.[i] in flags.(n) <- fl; end; done ;; let () = parse_options false "el";; let message = function | Partial_match "" -> "this pattern-matching is not exhaustive." | Partial_match s -> "this pattern-matching is not exhaustive.\n\ Here is an example of a value that is not matched:\n" ^ s | Unused_match -> "this match case is unused." | Unused_pat -> "this pattern is unused." | Fragile_pat "" -> "this pattern is fragile. It would hide\n\ the addition of new constructors to the data types it matches." | Fragile_pat s -> "this pattern is fragile. It would hide\n\ the addition of new constructors to the data types it matches.\n\ Here is an example of a more robust pattern:\n" ^ s | Labels_omitted -> "labels were omitted in the application of this function." | Method_override slist -> String.concat " " ("the following methods are overriden \ by the inherited class:\n " :: slist) | Hide_instance_variable lab -> "this definition of an instance variable " ^ lab ^ " hides a previously\ndefined instance variable of the same name." | Partial_application -> "this function application is partial,\n\ maybe some arguments are missing." | Statement_type -> "this expression should have type unit." | Comment s -> "this is " ^ s ^ "." | Deprecated -> "this syntax is deprecated." | Other s -> s ;; let nerrors = ref 0;; let print ppf w = let msg = message w in let newlines = ref 0 in for i = 0 to String.length msg - 1 do if msg.[i] = '\n' then incr newlines; done; let (out, flush, newline, space) = Format.pp_get_all_formatter_output_functions ppf () in let countnewline x = incr newlines; newline x in Format.pp_set_all_formatter_output_functions ppf out flush countnewline space; Format.fprintf ppf "%s" msg; Format.pp_print_flush ppf (); Format.pp_set_all_formatter_output_functions ppf out flush newline space; let (n, _) = translate (letter w) in if error.(n) then incr nerrors; !newlines ;; exception Errors of int;; let check_fatal () = if !nerrors > 0 then begin let e = Errors !nerrors in nerrors := 0; raise e; end; ;; ocamlweb-1.41/ocaml-parser/linenum.mli0000755000246300004300000000247413422556306017340 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1997 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* An auxiliary lexer for determining the line number corresponding to a file position, honoring the directives # linenum "filename" *) val for_position: string -> int -> string * int * int (* [Linenum.for_position file loc] returns a triple describing the location [loc] in the file named [file]. First result is name of actual source file. Second result is line number in that source file. Third result is position of beginning of that line in [file]. *) ocamlweb-1.41/ocaml-parser/linenum.mll0000755000246300004300000000503413422556306017336 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1997 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* An auxiliary lexer for determining the line number corresponding to a file position, honoring the directives # linenum "filename" *) { let filename = ref "" let linenum = ref 0 let linebeg = ref 0 let parse_sharp_line s = try (* Update the line number and file name *) let l1 = ref 0 in while let c = s.[!l1] in c < '0' || c > '9' do incr l1 done; let l2 = ref (!l1 + 1) in while let c = s.[!l2] in c >= '0' && c <= '9' do incr l2 done; linenum := int_of_string(String.sub s !l1 (!l2 - !l1)); let f1 = ref (!l2 + 1) in while !f1 < String.length s && s.[!f1] <> '"' do incr f1 done; let f2 = ref (!f1 + 1) in while !f2 < String.length s && s.[!f2] <> '"' do incr f2 done; if !f1 < String.length s then filename := String.sub s (!f1 + 1) (!f2 - !f1 - 1) with Failure _ | Invalid_argument _ -> Misc.fatal_error "Linenum.parse_sharp_line" } rule skip_line = parse "#" [' ' '\t']* ['0'-'9']+ [' ' '\t']* ("\"" [^ '\n' '\r' '"' (* '"' *) ] * "\"")? [^ '\n' '\r'] * ('\n' | '\r' | "\r\n") { parse_sharp_line(Lexing.lexeme lexbuf); linebeg := Lexing.lexeme_start lexbuf; Lexing.lexeme_end lexbuf } | [^ '\n' '\r'] * ('\n' | '\r' | "\r\n") { incr linenum; linebeg := Lexing.lexeme_start lexbuf; Lexing.lexeme_end lexbuf } | [^ '\n' '\r'] * eof { incr linenum; linebeg := Lexing.lexeme_start lexbuf; raise End_of_file } { let for_position file loc = let ic = open_in_bin file in let lb = Lexing.from_channel ic in filename := file; linenum := 1; linebeg := 0; begin try while skip_line lb <= loc do () done with End_of_file -> () end; close_in ic; (!filename, !linenum - 1, !linebeg) } ocamlweb-1.41/ocaml-parser/location.mli0000755000246300004300000000401013422556306017465 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Source code locations (ranges of positions), used in parsetree. *) open Format type t = { loc_start: Lexing.position; loc_end: Lexing.position; loc_ghost: bool; } (* Note on the use of Lexing.position in this module. If [pos_fname = ""], then use [!input_name] instead. If [pos_lnum = -1], then [pos_bol = 0]. Use [pos_cnum] and re-parse the file to get the line and character numbers. Else all fields are correct. *) val none : t (** An arbitrary value of type [t]; describes an empty ghost range. *) val init : Lexing.lexbuf -> string -> unit (** Set the file name and line number of the [lexbuf] to be the start of the named file. *) val curr : Lexing.lexbuf -> t (** Get the location of the current token from the [lexbuf]. *) val symbol_rloc: unit -> t val symbol_gloc: unit -> t val rhs_loc: int -> t val input_name: string ref val input_lexbuf: Lexing.lexbuf option ref val get_pos_info : Lexing.position -> string * int * int (* file, line, char *) val print: formatter -> t -> unit val print_warning: t -> formatter -> Warnings.t -> unit val prerr_warning: t -> Warnings.t -> unit val echo_eof: unit -> unit val reset: unit -> unit val highlight_locations: formatter -> t -> t -> bool ocamlweb-1.41/ocaml-parser/location.ml0000644000246300004300000001721513422556306017324 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) open Lexing type t = { loc_start: position; loc_end: position; loc_ghost: bool };; let none = { loc_start = dummy_pos; loc_end = dummy_pos; loc_ghost = true };; let curr lexbuf = { loc_start = lexbuf.lex_start_p; loc_end = lexbuf.lex_curr_p; loc_ghost = false };; let init lexbuf fname = lexbuf.lex_curr_p <- { pos_fname = fname; pos_lnum = 1; pos_bol = 0; pos_cnum = 0; } ;; let symbol_rloc () = { loc_start = Parsing.symbol_start_pos (); loc_end = Parsing.symbol_end_pos (); loc_ghost = false; };; let symbol_gloc () = { loc_start = Parsing.symbol_start_pos (); loc_end = Parsing.symbol_end_pos (); loc_ghost = true; };; let rhs_loc n = { loc_start = Parsing.rhs_start_pos n; loc_end = Parsing.rhs_end_pos n; loc_ghost = false; };; let input_name = ref "" let input_lexbuf = ref (None : lexbuf option) (* Terminal info *) let status = ref Terminfo.Uninitialised let num_loc_lines = ref 0 (* number of lines already printed after input *) (* Highlight the location using standout mode. *) let highlight_terminfo ppf num_lines lb loc1 loc2 = (* Char 0 is at offset -lb.lex_abs_pos in lb.lex_buffer. *) let pos0 = -lb.lex_abs_pos in (* Do nothing if the buffer does not contain the whole phrase. *) if pos0 < 0 then raise Exit; (* Count number of lines in phrase *) let lines = ref !num_loc_lines in for i = pos0 to lb.lex_buffer_len - 1 do if Bytes.get lb.lex_buffer i = '\n' then incr lines done; (* If too many lines, give up *) if !lines >= num_lines - 2 then raise Exit; (* Move cursor up that number of lines *) flush stdout; Terminfo.backup !lines; (* Print the input, switching to standout for the location *) let bol = ref false in print_string "# "; for pos = 0 to lb.lex_buffer_len - pos0 - 1 do if !bol then (print_string " "; bol := false); if pos = loc1.loc_start.pos_cnum || pos = loc2.loc_start.pos_cnum then Terminfo.standout true; if pos = loc1.loc_end.pos_cnum || pos = loc2.loc_end.pos_cnum then Terminfo.standout false; let c = Bytes.get lb.lex_buffer (pos + pos0) in print_char c; bol := (c = '\n') done; (* Make sure standout mode is over *) Terminfo.standout false; (* Position cursor back to original location *) Terminfo.resume !num_loc_lines; flush stdout (* Highlight the location by printing it again. *) let highlight_dumb ppf lb loc = (* Char 0 is at offset -lb.lex_abs_pos in lb.lex_buffer. *) let pos0 = -lb.lex_abs_pos in (* Do nothing if the buffer does not contain the whole phrase. *) if pos0 < 0 then raise Exit; let end_pos = lb.lex_buffer_len - pos0 - 1 in (* Determine line numbers for the start and end points *) let line_start = ref 0 and line_end = ref 0 in for pos = 0 to end_pos do if Bytes.get lb.lex_buffer (pos + pos0) = '\n' then begin if loc.loc_start.pos_cnum > pos then incr line_start; if loc.loc_end.pos_cnum > pos then incr line_end; end done; (* Print character location (useful for Emacs) *) Format.fprintf ppf "Characters %i-%i:@." loc.loc_start.pos_cnum loc.loc_end.pos_cnum; (* Print the input, underlining the location *) print_string " "; let line = ref 0 in let pos_at_bol = ref 0 in for pos = 0 to end_pos do let c = Bytes.get lb.lex_buffer (pos + pos0) in if c <> '\n' then begin if !line = !line_start && !line = !line_end then (* loc is on one line: print whole line *) print_char c else if !line = !line_start then (* first line of multiline loc: print ... before loc_start *) if pos < loc.loc_start.pos_cnum then print_char '.' else print_char c else if !line = !line_end then (* last line of multiline loc: print ... after loc_end *) if pos < loc.loc_end.pos_cnum then print_char c else print_char '.' else if !line > !line_start && !line < !line_end then (* intermediate line of multiline loc: print whole line *) print_char c end else begin if !line = !line_start && !line = !line_end then begin (* loc is on one line: underline location *) print_string "\n "; for i = !pos_at_bol to loc.loc_start.pos_cnum - 1 do print_char ' ' done; for i = loc.loc_start.pos_cnum to loc.loc_end.pos_cnum - 1 do print_char '^' done end; if !line >= !line_start && !line <= !line_end then begin print_char '\n'; if pos < loc.loc_end.pos_cnum then print_string " " end; incr line; pos_at_bol := pos + 1; end done (* Highlight the location using one of the supported modes. *) let rec highlight_locations ppf loc1 loc2 = match !status with Terminfo.Uninitialised -> status := Terminfo.setup stdout; highlight_locations ppf loc1 loc2 | Terminfo.Bad_term -> begin match !input_lexbuf with None -> false | Some lb -> let norepeat = try Sys.getenv "TERM" = "norepeat" with Not_found -> false in if norepeat then false else try highlight_dumb ppf lb loc1; true with Exit -> false end | Terminfo.Good_term num_lines -> begin match !input_lexbuf with None -> false | Some lb -> try highlight_terminfo ppf num_lines lb loc1 loc2; true with Exit -> false end (* Print the location in some way or another *) open Format let reset () = num_loc_lines := 0 let (msg_file, msg_line, msg_chars, msg_to, msg_colon, msg_head) = ("File \"", "\", line ", ", characters ", "-", ":", "") (* return file, line, char from the given position *) let get_pos_info pos = let (filename, linenum, linebeg) = if pos.pos_fname = "" && !input_name = "" then ("", -1, 0) else if pos.pos_fname = "" then Linenum.for_position !input_name pos.pos_cnum else (pos.pos_fname, pos.pos_lnum, pos.pos_bol) in (filename, linenum, pos.pos_cnum - linebeg) ;; let print ppf loc = let (file, line, startchar) = get_pos_info loc.loc_start in let endchar = loc.loc_end.pos_cnum - loc.loc_start.pos_cnum + startchar in if file = "" then begin if highlight_locations ppf loc none then () else fprintf ppf "Characters %i-%i:@." loc.loc_start.pos_cnum loc.loc_end.pos_cnum end else begin fprintf ppf "%s%s%s%i" msg_file file msg_line line; fprintf ppf "%s%i" msg_chars startchar; fprintf ppf "%s%i%s@.%s" msg_to endchar msg_colon msg_head; end let print_warning loc ppf w = if Warnings.is_active w then begin let printw ppf w = let n = Warnings.print ppf w in num_loc_lines := !num_loc_lines + n in fprintf ppf "%a" print loc; fprintf ppf "Warning: %a@." printw w; pp_print_flush ppf (); incr num_loc_lines; end ;; let prerr_warning loc w = print_warning loc err_formatter w;; let echo_eof () = print_newline (); incr num_loc_lines ocamlweb-1.41/ocaml-parser/longident.mli0000755000246300004300000000174613422556306017655 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Long identifiers, used in parsetree. *) type t = Lident of string | Ldot of t * string | Lapply of t * t val flatten: t -> string list val parse: string -> t ocamlweb-1.41/ocaml-parser/longident.ml0000755000246300004300000000302613422556306017475 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) type t = Lident of string | Ldot of t * string | Lapply of t * t let rec flat accu = function Lident s -> s :: accu | Ldot(lid, s) -> flat (s :: accu) lid | Lapply(l1, l2) -> Misc.fatal_error "Longident.flat" let flatten lid = flat [] lid let rec split_at_dots s pos = try let dot = String.index_from s pos '.' in String.sub s pos (dot - pos) :: split_at_dots s (dot + 1) with Not_found -> [String.sub s pos (String.length s - pos)] let parse s = match split_at_dots s 0 with [] -> Lident "" (* should not happen, but don't put assert false so as not to crash the toplevel (see Genprintval) *) | hd :: tl -> List.fold_left (fun p s -> Ldot(p, s)) (Lident hd) tl ocamlweb-1.41/ocaml-parser/syntaxerr.mli0000755000246300004300000000207013422556306017720 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1997 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Auxiliary type for reporting syntax errors *) open Format type error = Unclosed of Location.t * string * Location.t * string | Other of Location.t exception Error of error exception Escape_error val report_error: formatter -> error -> unit ocamlweb-1.41/ocaml-parser/syntaxerr.ml0000755000246300004300000000320713422556306017552 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1997 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Auxiliary type for reporting syntax errors *) open Format type error = Unclosed of Location.t * string * Location.t * string | Other of Location.t exception Error of error exception Escape_error let report_error ppf = function | Unclosed(opening_loc, opening, closing_loc, closing) -> if String.length !Location.input_name = 0 && Location.highlight_locations ppf opening_loc closing_loc then fprintf ppf "Syntax error: '%s' expected, \ the highlighted '%s' might be unmatched" closing opening else begin fprintf ppf "%aSyntax error: '%s' expected@." Location.print closing_loc closing; fprintf ppf "%aThis '%s' might be unmatched" Location.print opening_loc opening end | Other loc -> fprintf ppf "%aSyntax error" Location.print loc ocamlweb-1.41/ocaml-parser/asttypes.mli0000755000246300004300000000244313422556306017541 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Auxiliary a.s.t. types used by parsetree and typedtree. *) type constant = Const_int of int | Const_char of char | Const_string of string | Const_float of string | Const_int32 of int32 | Const_int64 of int64 | Const_nativeint of nativeint type rec_flag = Nonrecursive | Recursive | Default type direction_flag = Upto | Downto type private_flag = Private | Public type mutable_flag = Immutable | Mutable type virtual_flag = Virtual | Concrete type label = string ocamlweb-1.41/ocaml-parser/parsetree.mli0000755000246300004300000002115113422556306017654 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Abstract syntax tree produced by parsing *) open Asttypes (* Type expressions for the core language *) type core_type = { ptyp_desc: core_type_desc; ptyp_loc: Location.t } and core_type_desc = Ptyp_any | Ptyp_var of string | Ptyp_arrow of label * core_type * core_type | Ptyp_tuple of core_type list | Ptyp_constr of Longident.t * core_type list | Ptyp_object of core_field_type list | Ptyp_class of Longident.t * core_type list * label list | Ptyp_alias of core_type * string | Ptyp_variant of row_field list * bool * label list option | Ptyp_poly of string list * core_type and core_field_type = { pfield_desc: core_field_desc; pfield_loc: Location.t } and core_field_desc = Pfield of string * core_type | Pfield_var and row_field = Rtag of label * bool * core_type list | Rinherit of core_type (* XXX Type expressions for the class language *) type 'a class_infos = { pci_virt: virtual_flag; pci_params: string list * Location.t; pci_name: string; pci_expr: 'a; pci_variance: (bool * bool) list; pci_loc: Location.t } (* Value expressions for the core language *) type pattern = { ppat_desc: pattern_desc; ppat_loc: Location.t } and pattern_desc = Ppat_any | Ppat_var of string | Ppat_alias of pattern * string | Ppat_constant of constant | Ppat_tuple of pattern list | Ppat_construct of Longident.t * pattern option * bool | Ppat_variant of label * pattern option | Ppat_record of (Longident.t * pattern) list | Ppat_array of pattern list | Ppat_or of pattern * pattern | Ppat_constraint of pattern * core_type | Ppat_type of Longident.t type expression = { pexp_desc: expression_desc; pexp_loc: Location.t } and expression_desc = Pexp_ident of Longident.t | Pexp_constant of constant | Pexp_let of rec_flag * (pattern * expression) list * expression | Pexp_function of label * expression option * (pattern * expression) list | Pexp_apply of expression * (label * expression) list | Pexp_match of expression * (pattern * expression) list | Pexp_try of expression * (pattern * expression) list | Pexp_tuple of expression list | Pexp_construct of Longident.t * expression option * bool | Pexp_variant of label * expression option | Pexp_record of (Longident.t * expression) list * expression option | Pexp_field of expression * Longident.t | Pexp_setfield of expression * Longident.t * expression | Pexp_array of expression list | Pexp_ifthenelse of expression * expression * expression option | Pexp_sequence of expression * expression | Pexp_while of expression * expression | Pexp_for of string * expression * expression * direction_flag * expression | Pexp_constraint of expression * core_type option * core_type option | Pexp_when of expression * expression | Pexp_send of expression * string | Pexp_new of Longident.t | Pexp_setinstvar of string * expression | Pexp_override of (string * expression) list | Pexp_letmodule of string * module_expr * expression | Pexp_assert of expression | Pexp_assertfalse | Pexp_lazy of expression | Pexp_poly of expression * core_type option | Pexp_object of class_structure (* Value descriptions *) and value_description = { pval_type: core_type; pval_prim: string list } (* Type declarations *) and type_declaration = { ptype_params: string list; ptype_cstrs: (core_type * core_type * Location.t) list; ptype_kind: type_kind; ptype_manifest: core_type option; ptype_variance: (bool * bool) list; ptype_loc: Location.t } and type_kind = Ptype_abstract | Ptype_variant of (string * core_type list) list * private_flag | Ptype_record of (string * mutable_flag * core_type) list * private_flag and exception_declaration = core_type list (* Type expressions for the class language *) and class_type = { pcty_desc: class_type_desc; pcty_loc: Location.t } and class_type_desc = Pcty_constr of Longident.t * core_type list | Pcty_signature of class_signature | Pcty_fun of label * core_type * class_type and class_signature = core_type * class_type_field list and class_type_field = Pctf_inher of class_type | Pctf_val of (string * mutable_flag * core_type option * Location.t) | Pctf_virt of (string * private_flag * core_type * Location.t) | Pctf_meth of (string * private_flag * core_type * Location.t) | Pctf_cstr of (core_type * core_type * Location.t) and class_description = class_type class_infos and class_type_declaration = class_type class_infos (* Value expressions for the class language *) and class_expr = { pcl_desc: class_expr_desc; pcl_loc: Location.t } and class_expr_desc = Pcl_constr of Longident.t * core_type list | Pcl_structure of class_structure | Pcl_fun of label * expression option * pattern * class_expr | Pcl_apply of class_expr * (label * expression) list | Pcl_let of rec_flag * (pattern * expression) list * class_expr | Pcl_constraint of class_expr * class_type and class_structure = pattern * class_field list and class_field = Pcf_inher of class_expr * string option | Pcf_val of (string * mutable_flag * expression * Location.t) | Pcf_virt of (string * private_flag * core_type * Location.t) | Pcf_meth of (string * private_flag * expression * Location.t) | Pcf_cstr of (core_type * core_type * Location.t) | Pcf_let of rec_flag * (pattern * expression) list * Location.t | Pcf_init of expression and class_declaration = class_expr class_infos (* Type expressions for the module language *) and module_type = { pmty_desc: module_type_desc; pmty_loc: Location.t } and module_type_desc = Pmty_ident of Longident.t | Pmty_signature of signature | Pmty_functor of string * module_type * module_type | Pmty_with of module_type * (Longident.t * with_constraint) list and signature = signature_item list and signature_item = { psig_desc: signature_item_desc; psig_loc: Location.t } and signature_item_desc = Psig_value of string * value_description | Psig_type of (string * type_declaration) list | Psig_exception of string * exception_declaration | Psig_module of string * module_type | Psig_recmodule of (string * module_type) list | Psig_modtype of string * modtype_declaration | Psig_open of Longident.t | Psig_include of module_type | Psig_class of class_description list | Psig_class_type of class_type_declaration list and modtype_declaration = Pmodtype_abstract | Pmodtype_manifest of module_type and with_constraint = Pwith_type of type_declaration | Pwith_module of Longident.t (* Value expressions for the module language *) and module_expr = { pmod_desc: module_expr_desc; pmod_loc: Location.t } and module_expr_desc = Pmod_ident of Longident.t | Pmod_structure of structure | Pmod_functor of string * module_type * module_expr | Pmod_apply of module_expr * module_expr | Pmod_constraint of module_expr * module_type and structure = structure_item list and structure_item = { pstr_desc: structure_item_desc; pstr_loc: Location.t } and structure_item_desc = Pstr_eval of expression | Pstr_value of rec_flag * (pattern * expression) list | Pstr_primitive of string * value_description | Pstr_type of (string * type_declaration) list | Pstr_exception of string * exception_declaration | Pstr_exn_rebind of string * Longident.t | Pstr_module of string * module_expr | Pstr_recmodule of (string * module_type * module_expr) list | Pstr_modtype of string * module_type | Pstr_open of Longident.t | Pstr_class of class_declaration list | Pstr_class_type of class_type_declaration list | Pstr_include of module_expr (* Toplevel phrases *) type toplevel_phrase = Ptop_def of structure | Ptop_dir of string * directive_argument and directive_argument = Pdir_none | Pdir_string of string | Pdir_int of int | Pdir_ident of Longident.t | Pdir_bool of bool ocamlweb-1.41/ocaml-parser/parser.mly0000755000246300004300000014270413422556306017206 0ustar filliatrvals/***********************************************************************/ /* */ /* Objective Caml */ /* */ /* Xavier Leroy, projet Cristal, INRIA Rocquencourt */ /* */ /* Copyright 1996 Institut National de Recherche en Informatique et */ /* en Automatique. All rights reserved. This file is distributed */ /* under the terms of the Q Public License version 1.0. */ /* */ /***********************************************************************/ /* $Id$ */ /* The parser definition */ %{ open Location open Asttypes open Longident open Parsetree let mktyp d = { ptyp_desc = d; ptyp_loc = symbol_rloc() } let mkpat d = { ppat_desc = d; ppat_loc = symbol_rloc() } let mkexp d = { pexp_desc = d; pexp_loc = symbol_rloc() } let mkmty d = { pmty_desc = d; pmty_loc = symbol_rloc() } let mksig d = { psig_desc = d; psig_loc = symbol_rloc() } let mkmod d = { pmod_desc = d; pmod_loc = symbol_rloc() } let mkstr d = { pstr_desc = d; pstr_loc = symbol_rloc() } let mkfield d = { pfield_desc = d; pfield_loc = symbol_rloc() } let mkclass d = { pcl_desc = d; pcl_loc = symbol_rloc() } let mkcty d = { pcty_desc = d; pcty_loc = symbol_rloc() } let reloc_pat x = { x with ppat_loc = symbol_rloc () };; let reloc_exp x = { x with pexp_loc = symbol_rloc () };; let mkoperator name pos = { pexp_desc = Pexp_ident(Lident name); pexp_loc = rhs_loc pos } (* Ghost expressions and patterns: expressions and patterns that do not appear explicitely in the source file they have the loc_ghost flag set to true. Then the profiler will not try to instrument them and the -stypes option will not try to display their type. Every grammar rule that generates an element with a location must make at most one non-ghost element, the topmost one. How to tell whether your location must be ghost: A location corresponds to a range of characters in the source file. If the location contains a piece of code that is syntactically valid (according to the documentation), and corresponds to the AST node, then the location must be real; in all other cases, it must be ghost. *) let ghexp d = { pexp_desc = d; pexp_loc = symbol_gloc () };; let ghpat d = { ppat_desc = d; ppat_loc = symbol_gloc () };; let ghtyp d = { ptyp_desc = d; ptyp_loc = symbol_gloc () };; let mkassert e = match e with | {pexp_desc = Pexp_construct (Lident "false", None, false) } -> mkexp (Pexp_assertfalse) | _ -> mkexp (Pexp_assert (e)) ;; let mkinfix arg1 name arg2 = mkexp(Pexp_apply(mkoperator name 2, ["", arg1; "", arg2])) let neg_float_string f = if String.length f > 0 && f.[0] = '-' then String.sub f 1 (String.length f - 1) else "-" ^ f let mkuminus name arg = match name, arg.pexp_desc with | "-", Pexp_constant(Const_int n) -> mkexp(Pexp_constant(Const_int(-n))) | "-", Pexp_constant(Const_int32 n) -> mkexp(Pexp_constant(Const_int32(Int32.neg n))) | "-", Pexp_constant(Const_int64 n) -> mkexp(Pexp_constant(Const_int64(Int64.neg n))) | "-", Pexp_constant(Const_nativeint n) -> mkexp(Pexp_constant(Const_nativeint(Nativeint.neg n))) | _, Pexp_constant(Const_float f) -> mkexp(Pexp_constant(Const_float(neg_float_string f))) | _ -> mkexp(Pexp_apply(mkoperator ("~" ^ name) 1, ["", arg])) let rec mktailexp = function [] -> ghexp(Pexp_construct(Lident "[]", None, false)) | e1 :: el -> let exp_el = mktailexp el in let l = {loc_start = e1.pexp_loc.loc_start; loc_end = exp_el.pexp_loc.loc_end; loc_ghost = true} in let arg = {pexp_desc = Pexp_tuple [e1; exp_el]; pexp_loc = l} in {pexp_desc = Pexp_construct(Lident "::", Some arg, false); pexp_loc = l} let rec mktailpat = function [] -> ghpat(Ppat_construct(Lident "[]", None, false)) | p1 :: pl -> let pat_pl = mktailpat pl in let l = {loc_start = p1.ppat_loc.loc_start; loc_end = pat_pl.ppat_loc.loc_end; loc_ghost = true} in let arg = {ppat_desc = Ppat_tuple [p1; pat_pl]; ppat_loc = l} in {ppat_desc = Ppat_construct(Lident "::", Some arg, false); ppat_loc = l} let ghstrexp e = { pstr_desc = Pstr_eval e; pstr_loc = {e.pexp_loc with loc_ghost = true} } let array_function str name = Ldot(Lident str, (if !Clflags.fast then "unsafe_" ^ name else name)) let rec deep_mkrangepat c1 c2 = if c1 = c2 then ghpat(Ppat_constant(Const_char c1)) else ghpat(Ppat_or(ghpat(Ppat_constant(Const_char c1)), deep_mkrangepat (Char.chr(Char.code c1 + 1)) c2)) let rec mkrangepat c1 c2 = if c1 > c2 then mkrangepat c2 c1 else if c1 = c2 then mkpat(Ppat_constant(Const_char c1)) else reloc_pat (deep_mkrangepat c1 c2) let syntax_error () = raise Syntaxerr.Escape_error let unclosed opening_name opening_num closing_name closing_num = raise(Syntaxerr.Error(Syntaxerr.Unclosed(rhs_loc opening_num, opening_name, rhs_loc closing_num, closing_name))) let bigarray_function str name = Ldot(Ldot(Lident "Bigarray", str), name) let bigarray_untuplify = function { pexp_desc = Pexp_tuple explist} -> explist | exp -> [exp] let bigarray_get arr arg = match bigarray_untuplify arg with [c1] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array1" "get")), ["", arr; "", c1])) | [c1;c2] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array2" "get")), ["", arr; "", c1; "", c2])) | [c1;c2;c3] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array3" "get")), ["", arr; "", c1; "", c2; "", c3])) | coords -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Genarray" "get")), ["", arr; "", ghexp(Pexp_array coords)])) let bigarray_set arr arg newval = match bigarray_untuplify arg with [c1] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array1" "set")), ["", arr; "", c1; "", newval])) | [c1;c2] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array2" "set")), ["", arr; "", c1; "", c2; "", newval])) | [c1;c2;c3] -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Array3" "set")), ["", arr; "", c1; "", c2; "", c3; "", newval])) | coords -> mkexp(Pexp_apply(ghexp(Pexp_ident(bigarray_function "Genarray" "set")), ["", arr; "", ghexp(Pexp_array coords); "", newval])) %} /* Tokens */ %token AMPERAMPER %token AMPERSAND %token AND %token AS %token ASSERT %token BACKQUOTE %token BAR %token BARBAR %token BARRBRACKET %token BEGIN %token CHAR %token CLASS %token COLON %token COLONCOLON %token COLONEQUAL %token COLONGREATER %token COMMA %token CONSTRAINT %token DO %token DONE %token DOT %token DOTDOT %token DOWNTO %token ELSE %token END %token EOF %token EQUAL %token EXCEPTION %token EXTERNAL %token FALSE %token FLOAT %token FOR %token FUN %token FUNCTION %token FUNCTOR %token GREATER %token GREATERRBRACE %token GREATERRBRACKET %token IF %token IN %token INCLUDE %token INFIXOP0 %token INFIXOP1 %token INFIXOP2 %token INFIXOP3 %token INFIXOP4 %token INHERIT %token INITIALIZER %token INT %token INT32 %token INT64 %token LABEL %token LAZY %token LBRACE %token LBRACELESS %token LBRACKET %token LBRACKETBAR %token LBRACKETLESS %token LBRACKETGREATER %token LESS %token LESSMINUS %token LET %token LIDENT %token LPAREN %token MATCH %token METHOD %token MINUS %token MINUSDOT %token MINUSGREATER %token MODULE %token MUTABLE %token NATIVEINT %token NEW %token OBJECT %token OF %token OPEN %token OPTLABEL %token OR /* %token PARSER */ %token PLUS %token PREFIXOP %token PRIVATE %token QUESTION %token QUESTIONQUESTION %token QUOTE %token RBRACE %token RBRACKET %token REC %token RPAREN %token SEMI %token SEMISEMI %token SHARP %token SIG %token STAR %token STRING %token STRUCT %token THEN %token TILDE %token TO %token TRUE %token TRY %token TYPE %token UIDENT %token UNDERSCORE %token VAL %token VIRTUAL %token WHEN %token WHILE %token WITH /* Precedences and associativities. Tokens and rules have precedences. A reduce/reduce conflict is resolved in favor of the first rule (in source file order). A shift/reduce conflict is resolved by comparing the precedence and associativity of the token to be shifted with those of the rule to be reduced. By default, a rule has the precedence of its rightmost terminal (if any). When there is a shift/reduce conflict between a rule and a token that have the same precedence, it is resolved using the associativity: if the token is left-associative, the parser will reduce; if right-associative, the parser will shift; if non-associative, the parser will declare a syntax error. We will only use associativities with operators of the kind x * x -> x for example, in the rules of the form expr: expr BINOP expr in all other cases, we define two precedences if needed to resolve conflicts. The precedences must be listed from low to high. */ %nonassoc IN %nonassoc below_SEMI %nonassoc SEMI /* below EQUAL ({lbl=...; lbl=...}) */ %nonassoc LET /* above SEMI ( ...; let ... in ...) */ %nonassoc below_WITH %nonassoc FUNCTION WITH /* below BAR (match ... with ...) */ %nonassoc AND /* above WITH (module rec A: SIG with ... and ...) */ %nonassoc THEN /* below ELSE (if ... then ...) */ %nonassoc ELSE /* (if ... then ... else ...) */ %nonassoc LESSMINUS /* below COLONEQUAL (lbl <- x := e) */ %right COLONEQUAL /* expr (e := e := e) */ %nonassoc AS %left BAR /* pattern (p|p|p) */ %nonassoc below_COMMA %left COMMA /* expr/expr_comma_list (e,e,e) */ %right MINUSGREATER /* core_type2 (t -> t -> t) */ %right OR BARBAR /* expr (e || e || e) */ %right AMPERSAND AMPERAMPER /* expr (e && e && e) */ %nonassoc below_EQUAL %left INFIXOP0 EQUAL LESS GREATER /* expr (e OP e OP e) */ %right INFIXOP1 /* expr (e OP e OP e) */ %right COLONCOLON /* expr (e :: e :: e) */ %left INFIXOP2 PLUS MINUS MINUSDOT /* expr (e OP e OP e) */ %left INFIXOP3 STAR /* expr (e OP e OP e) */ %right INFIXOP4 /* expr (e OP e OP e) */ %nonassoc prec_unary_minus /* unary - */ %nonassoc prec_constant_constructor /* cf. simple_expr (C versus C x) */ %nonassoc prec_constr_appl /* above AS BAR COLONCOLON COMMA */ %nonassoc below_SHARP %nonassoc SHARP /* simple_expr/toplevel_directive */ %nonassoc below_DOT %nonassoc DOT /* Finally, the first tokens of simple_expr are above everything else. */ %nonassoc BACKQUOTE BEGIN CHAR FALSE FLOAT INT INT32 INT64 LBRACE LBRACELESS LBRACKET LBRACKETBAR LIDENT LPAREN NEW NATIVEINT PREFIXOP STRING TRUE UIDENT /* Entry points */ %start implementation /* for implementation files */ %type implementation %start interface /* for interface files */ %type interface %start toplevel_phrase /* for interactive use */ %type toplevel_phrase %start use_file /* for the #use directive */ %type use_file %% /* Entry points */ implementation: structure EOF { $1 } ; interface: signature EOF { List.rev $1 } ; toplevel_phrase: top_structure SEMISEMI { Ptop_def $1 } | seq_expr SEMISEMI { Ptop_def[ghstrexp $1] } | toplevel_directive SEMISEMI { $1 } | EOF { raise End_of_file } ; top_structure: structure_item { [$1] } | structure_item top_structure { $1 :: $2 } ; use_file: use_file_tail { $1 } | seq_expr use_file_tail { Ptop_def[ghstrexp $1] :: $2 } ; use_file_tail: EOF { [] } | SEMISEMI EOF { [] } | SEMISEMI seq_expr use_file_tail { Ptop_def[ghstrexp $2] :: $3 } | SEMISEMI structure_item use_file_tail { Ptop_def[$2] :: $3 } | SEMISEMI toplevel_directive use_file_tail { $2 :: $3 } | structure_item use_file_tail { Ptop_def[$1] :: $2 } | toplevel_directive use_file_tail { $1 :: $2 } ; /* Module expressions */ module_expr: mod_longident { mkmod(Pmod_ident $1) } | STRUCT structure END { mkmod(Pmod_structure($2)) } | STRUCT structure error { unclosed "struct" 1 "end" 3 } | FUNCTOR LPAREN UIDENT COLON module_type RPAREN MINUSGREATER module_expr { mkmod(Pmod_functor($3, $5, $8)) } | module_expr LPAREN module_expr RPAREN { mkmod(Pmod_apply($1, $3)) } | module_expr LPAREN module_expr error { unclosed "(" 2 ")" 4 } | LPAREN module_expr COLON module_type RPAREN { mkmod(Pmod_constraint($2, $4)) } | LPAREN module_expr COLON module_type error { unclosed "(" 1 ")" 5 } | LPAREN module_expr RPAREN { $2 } | LPAREN module_expr error { unclosed "(" 1 ")" 3 } ; structure: structure_tail { $1 } | seq_expr structure_tail { ghstrexp $1 :: $2 } ; structure_tail: /* empty */ { [] } | SEMISEMI { [] } | SEMISEMI seq_expr structure_tail { ghstrexp $2 :: $3 } | SEMISEMI structure_item structure_tail { $2 :: $3 } | structure_item structure_tail { $1 :: $2 } ; structure_item: LET rec_flag let_bindings { match $3 with [{ppat_desc = Ppat_any}, exp] -> mkstr(Pstr_eval exp) | _ -> mkstr(Pstr_value($2, List.rev $3)) } | EXTERNAL val_ident_colon core_type EQUAL primitive_declaration { mkstr(Pstr_primitive($2, {pval_type = $3; pval_prim = $5})) } | TYPE type_declarations { mkstr(Pstr_type(List.rev $2)) } | EXCEPTION UIDENT constructor_arguments { mkstr(Pstr_exception($2, $3)) } | EXCEPTION UIDENT EQUAL constr_longident { mkstr(Pstr_exn_rebind($2, $4)) } | MODULE UIDENT module_binding { mkstr(Pstr_module($2, $3)) } | MODULE REC module_rec_bindings { mkstr(Pstr_recmodule(List.rev $3)) } | MODULE TYPE ident EQUAL module_type { mkstr(Pstr_modtype($3, $5)) } | OPEN mod_longident { mkstr(Pstr_open $2) } | CLASS class_declarations { mkstr(Pstr_class (List.rev $2)) } | CLASS TYPE class_type_declarations { mkstr(Pstr_class_type (List.rev $3)) } | INCLUDE module_expr { mkstr(Pstr_include $2) } ; module_binding: EQUAL module_expr { $2 } | COLON module_type EQUAL module_expr { mkmod(Pmod_constraint($4, $2)) } | LPAREN UIDENT COLON module_type RPAREN module_binding { mkmod(Pmod_functor($2, $4, $6)) } ; module_rec_bindings: module_rec_binding { [$1] } | module_rec_bindings AND module_rec_binding { $3 :: $1 } ; module_rec_binding: UIDENT COLON module_type EQUAL module_expr { ($1, $3, $5) } ; /* Module types */ module_type: mty_longident { mkmty(Pmty_ident $1) } | SIG signature END { mkmty(Pmty_signature(List.rev $2)) } | SIG signature error { unclosed "sig" 1 "end" 3 } | FUNCTOR LPAREN UIDENT COLON module_type RPAREN MINUSGREATER module_type %prec below_WITH { mkmty(Pmty_functor($3, $5, $8)) } | module_type WITH with_constraints { mkmty(Pmty_with($1, List.rev $3)) } | LPAREN module_type RPAREN { $2 } | LPAREN module_type error { unclosed "(" 1 ")" 3 } ; signature: /* empty */ { [] } | signature signature_item { $2 :: $1 } | signature signature_item SEMISEMI { $2 :: $1 } ; signature_item: VAL val_ident_colon core_type { mksig(Psig_value($2, {pval_type = $3; pval_prim = []})) } | EXTERNAL val_ident_colon core_type EQUAL primitive_declaration { mksig(Psig_value($2, {pval_type = $3; pval_prim = $5})) } | TYPE type_declarations { mksig(Psig_type(List.rev $2)) } | EXCEPTION UIDENT constructor_arguments { mksig(Psig_exception($2, $3)) } | MODULE UIDENT module_declaration { mksig(Psig_module($2, $3)) } | MODULE REC module_rec_declarations { mksig(Psig_recmodule(List.rev $3)) } | MODULE TYPE ident { mksig(Psig_modtype($3, Pmodtype_abstract)) } | MODULE TYPE ident EQUAL module_type { mksig(Psig_modtype($3, Pmodtype_manifest $5)) } | OPEN mod_longident { mksig(Psig_open $2) } | INCLUDE module_type { mksig(Psig_include $2) } | CLASS class_descriptions { mksig(Psig_class (List.rev $2)) } | CLASS TYPE class_type_declarations { mksig(Psig_class_type (List.rev $3)) } ; module_declaration: COLON module_type { $2 } | LPAREN UIDENT COLON module_type RPAREN module_declaration { mkmty(Pmty_functor($2, $4, $6)) } ; module_rec_declarations: module_rec_declaration { [$1] } | module_rec_declarations AND module_rec_declaration { $3 :: $1 } ; module_rec_declaration: UIDENT COLON module_type { ($1, $3) } ; /* Class expressions */ class_declarations: class_declarations AND class_declaration { $3 :: $1 } | class_declaration { [$1] } ; class_declaration: virtual_flag class_type_parameters LIDENT class_fun_binding { let params, variance = List.split (fst $2) in {pci_virt = $1; pci_params = params, snd $2; pci_name = $3; pci_expr = $4; pci_variance = variance; pci_loc = symbol_rloc ()} } ; class_fun_binding: EQUAL class_expr { $2 } | COLON class_type EQUAL class_expr { mkclass(Pcl_constraint($4, $2)) } | labeled_simple_pattern class_fun_binding { let (l,o,p) = $1 in mkclass(Pcl_fun(l, o, p, $2)) } ; class_type_parameters: /*empty*/ { [], symbol_gloc () } | LBRACKET type_parameter_list RBRACKET { List.rev $2, symbol_rloc () } ; class_fun_def: labeled_simple_pattern MINUSGREATER class_expr { let (l,o,p) = $1 in mkclass(Pcl_fun(l, o, p, $3)) } | labeled_simple_pattern class_fun_def { let (l,o,p) = $1 in mkclass(Pcl_fun(l, o, p, $2)) } ; class_expr: class_simple_expr { $1 } | FUN class_fun_def { $2 } | class_simple_expr simple_labeled_expr_list { mkclass(Pcl_apply($1, List.rev $2)) } | LET rec_flag let_bindings IN class_expr { mkclass(Pcl_let ($2, List.rev $3, $5)) } ; class_simple_expr: LBRACKET core_type_comma_list RBRACKET class_longident { mkclass(Pcl_constr($4, List.rev $2)) } | class_longident { mkclass(Pcl_constr($1, [])) } | OBJECT class_structure END { mkclass(Pcl_structure($2)) } | OBJECT class_structure error { unclosed "object" 1 "end" 3 } | LPAREN class_expr COLON class_type RPAREN { mkclass(Pcl_constraint($2, $4)) } | LPAREN class_expr COLON class_type error { unclosed "(" 1 ")" 5 } | LPAREN class_expr RPAREN { $2 } | LPAREN class_expr error { unclosed "(" 1 ")" 3 } ; class_structure: class_self_pattern class_fields { $1, List.rev $2 } ; class_self_pattern: LPAREN pattern RPAREN { reloc_pat $2 } | LPAREN pattern COLON core_type RPAREN { mkpat(Ppat_constraint($2, $4)) } | /* empty */ { ghpat(Ppat_any) } ; class_fields: /* empty */ { [] } | class_fields INHERIT class_expr parent_binder { Pcf_inher ($3, $4) :: $1 } | class_fields VAL value { Pcf_val $3 :: $1 } | class_fields virtual_method { Pcf_virt $2 :: $1 } | class_fields concrete_method { Pcf_meth $2 :: $1 } | class_fields CONSTRAINT constrain { Pcf_cstr $3 :: $1 } | class_fields INITIALIZER seq_expr { Pcf_init $3 :: $1 } ; parent_binder: AS LIDENT { Some $2 } | /* empty */ {None} ; value: mutable_flag label EQUAL seq_expr { $2, $1, $4, symbol_rloc () } | mutable_flag label type_constraint EQUAL seq_expr { $2, $1, (let (t, t') = $3 in ghexp(Pexp_constraint($5, t, t'))), symbol_rloc () } ; virtual_method: METHOD PRIVATE VIRTUAL label COLON poly_type { $4, Private, $6, symbol_rloc () } | METHOD VIRTUAL private_flag label COLON poly_type { $4, $3, $6, symbol_rloc () } ; concrete_method : METHOD private_flag label strict_binding { $3, $2, ghexp(Pexp_poly ($4, None)), symbol_rloc () } | METHOD private_flag label COLON poly_type EQUAL seq_expr { $3, $2, ghexp(Pexp_poly($7,Some $5)), symbol_rloc () } | METHOD private_flag LABEL poly_type EQUAL seq_expr { $3, $2, ghexp(Pexp_poly($6,Some $4)), symbol_rloc () } ; /* Class types */ class_type: class_signature { $1 } | QUESTION LIDENT COLON simple_core_type_or_tuple MINUSGREATER class_type { mkcty(Pcty_fun("?" ^ $2 , {ptyp_desc = Ptyp_constr(Lident "option", [$4]); ptyp_loc = $4.ptyp_loc}, $6)) } | OPTLABEL simple_core_type_or_tuple MINUSGREATER class_type { mkcty(Pcty_fun("?" ^ $1 , {ptyp_desc = Ptyp_constr(Lident "option", [$2]); ptyp_loc = $2.ptyp_loc}, $4)) } | LIDENT COLON simple_core_type_or_tuple MINUSGREATER class_type { mkcty(Pcty_fun($1, $3, $5)) } | simple_core_type_or_tuple MINUSGREATER class_type { mkcty(Pcty_fun("", $1, $3)) } ; class_signature: LBRACKET core_type_comma_list RBRACKET clty_longident { mkcty(Pcty_constr ($4, List.rev $2)) } | clty_longident { mkcty(Pcty_constr ($1, [])) } | OBJECT class_sig_body END { mkcty(Pcty_signature $2) } | OBJECT class_sig_body error { unclosed "object" 1 "end" 3 } ; class_sig_body: class_self_type class_sig_fields { $1, List.rev $2 } ; class_self_type: LPAREN core_type RPAREN { $2 } | /* empty */ { mktyp(Ptyp_any) } ; class_sig_fields: /* empty */ { [] } | class_sig_fields INHERIT class_signature { Pctf_inher $3 :: $1 } | class_sig_fields VAL value_type { Pctf_val $3 :: $1 } | class_sig_fields virtual_method { Pctf_virt $2 :: $1 } | class_sig_fields method_type { Pctf_meth $2 :: $1 } | class_sig_fields CONSTRAINT constrain { Pctf_cstr $3 :: $1 } ; value_type: mutable_flag label COLON core_type { $2, $1, Some $4, symbol_rloc () } ; method_type: METHOD private_flag label COLON poly_type { $3, $2, $5, symbol_rloc () } ; constrain: core_type EQUAL core_type { $1, $3, symbol_rloc () } ; class_descriptions: class_descriptions AND class_description { $3 :: $1 } | class_description { [$1] } ; class_description: virtual_flag class_type_parameters LIDENT COLON class_type { let params, variance = List.split (fst $2) in {pci_virt = $1; pci_params = params, snd $2; pci_name = $3; pci_expr = $5; pci_variance = variance; pci_loc = symbol_rloc ()} } ; class_type_declarations: class_type_declarations AND class_type_declaration { $3 :: $1 } | class_type_declaration { [$1] } ; class_type_declaration: virtual_flag class_type_parameters LIDENT EQUAL class_signature { let params, variance = List.split (fst $2) in {pci_virt = $1; pci_params = params, snd $2; pci_name = $3; pci_expr = $5; pci_variance = variance; pci_loc = symbol_rloc ()} } ; /* Core expressions */ seq_expr: | expr %prec below_SEMI { $1 } | expr SEMI { reloc_exp $1 } | expr SEMI seq_expr { mkexp(Pexp_sequence($1, $3)) } ; labeled_simple_pattern: QUESTION LPAREN label_let_pattern opt_default RPAREN { ("?" ^ fst $3, $4, snd $3) } | QUESTION label_var { ("?" ^ fst $2, None, snd $2) } | OPTLABEL LPAREN let_pattern opt_default RPAREN { ("?" ^ $1, $4, $3) } | OPTLABEL pattern_var { ("?" ^ $1, None, $2) } | TILDE LPAREN label_let_pattern RPAREN { (fst $3, None, snd $3) } | TILDE label_var { (fst $2, None, snd $2) } | LABEL simple_pattern { ($1, None, $2) } | simple_pattern { ("", None, $1) } ; pattern_var: LIDENT { mkpat(Ppat_var $1) } ; opt_default: /* empty */ { None } | EQUAL seq_expr { Some $2 } ; label_let_pattern: label_var { $1 } | label_var COLON core_type { let (lab, pat) = $1 in (lab, mkpat(Ppat_constraint(pat, $3))) } ; label_var: LIDENT { ($1, mkpat(Ppat_var $1)) } ; let_pattern: pattern { $1 } | pattern COLON core_type { mkpat(Ppat_constraint($1, $3)) } ; expr: simple_expr %prec below_SHARP { $1 } | simple_expr simple_labeled_expr_list { mkexp(Pexp_apply($1, List.rev $2)) } | LET rec_flag let_bindings IN seq_expr { mkexp(Pexp_let($2, List.rev $3, $5)) } | LET MODULE UIDENT module_binding IN seq_expr { mkexp(Pexp_letmodule($3, $4, $6)) } | FUNCTION opt_bar match_cases { mkexp(Pexp_function("", None, List.rev $3)) } | FUN labeled_simple_pattern fun_def { let (l,o,p) = $2 in mkexp(Pexp_function(l, o, [p, $3])) } | MATCH seq_expr WITH opt_bar match_cases { mkexp(Pexp_match($2, List.rev $5)) } | TRY seq_expr WITH opt_bar match_cases { mkexp(Pexp_try($2, List.rev $5)) } | TRY seq_expr WITH error { syntax_error() } | expr_comma_list %prec below_COMMA { mkexp(Pexp_tuple(List.rev $1)) } | constr_longident simple_expr %prec below_SHARP { mkexp(Pexp_construct($1, Some $2, false)) } | name_tag simple_expr %prec below_SHARP { mkexp(Pexp_variant($1, Some $2)) } | IF seq_expr THEN expr ELSE expr { mkexp(Pexp_ifthenelse($2, $4, Some $6)) } | IF seq_expr THEN expr { mkexp(Pexp_ifthenelse($2, $4, None)) } | WHILE seq_expr DO seq_expr DONE { mkexp(Pexp_while($2, $4)) } | FOR val_ident EQUAL seq_expr direction_flag seq_expr DO seq_expr DONE { mkexp(Pexp_for($2, $4, $6, $5, $8)) } | expr COLONCOLON expr { mkexp(Pexp_construct(Lident "::", Some(ghexp(Pexp_tuple[$1;$3])), false)) } | expr INFIXOP0 expr { mkinfix $1 $2 $3 } | expr INFIXOP1 expr { mkinfix $1 $2 $3 } | expr INFIXOP2 expr { mkinfix $1 $2 $3 } | expr INFIXOP3 expr { mkinfix $1 $2 $3 } | expr INFIXOP4 expr { mkinfix $1 $2 $3 } | expr PLUS expr { mkinfix $1 "+" $3 } | expr MINUS expr { mkinfix $1 "-" $3 } | expr MINUSDOT expr { mkinfix $1 "-." $3 } | expr STAR expr { mkinfix $1 "*" $3 } | expr EQUAL expr { mkinfix $1 "=" $3 } | expr LESS expr { mkinfix $1 "<" $3 } | expr GREATER expr { mkinfix $1 ">" $3 } | expr OR expr { mkinfix $1 "or" $3 } | expr BARBAR expr { mkinfix $1 "||" $3 } | expr AMPERSAND expr { mkinfix $1 "&" $3 } | expr AMPERAMPER expr { mkinfix $1 "&&" $3 } | expr COLONEQUAL expr { mkinfix $1 ":=" $3 } | subtractive expr %prec prec_unary_minus { mkuminus $1 $2 } | simple_expr DOT label_longident LESSMINUS expr { mkexp(Pexp_setfield($1, $3, $5)) } | simple_expr DOT LPAREN seq_expr RPAREN LESSMINUS expr { mkexp(Pexp_apply(ghexp(Pexp_ident(array_function "Array" "set")), ["",$1; "",$4; "",$7])) } | simple_expr DOT LBRACKET seq_expr RBRACKET LESSMINUS expr { mkexp(Pexp_apply(ghexp(Pexp_ident(array_function "String" "set")), ["",$1; "",$4; "",$7])) } | simple_expr DOT LBRACE expr RBRACE LESSMINUS expr { bigarray_set $1 $4 $7 } | label LESSMINUS expr { mkexp(Pexp_setinstvar($1, $3)) } | ASSERT simple_expr %prec below_SHARP { mkassert $2 } | LAZY simple_expr %prec below_SHARP { mkexp (Pexp_lazy ($2)) } | OBJECT class_structure END { mkexp (Pexp_object($2)) } | OBJECT class_structure error { unclosed "object" 1 "end" 3 } ; simple_expr: val_longident { mkexp(Pexp_ident $1) } | constant { mkexp(Pexp_constant $1) } | constr_longident %prec prec_constant_constructor { mkexp(Pexp_construct($1, None, false)) } | name_tag %prec prec_constant_constructor { mkexp(Pexp_variant($1, None)) } | LPAREN seq_expr RPAREN { reloc_exp $2 } | LPAREN seq_expr error { unclosed "(" 1 ")" 3 } | BEGIN seq_expr END { reloc_exp $2 } | BEGIN END { mkexp (Pexp_construct (Lident "()", None, false)) } | BEGIN seq_expr error { unclosed "begin" 1 "end" 3 } | LPAREN seq_expr type_constraint RPAREN { let (t, t') = $3 in mkexp(Pexp_constraint($2, t, t')) } | simple_expr DOT label_longident { mkexp(Pexp_field($1, $3)) } | simple_expr DOT LPAREN seq_expr RPAREN { mkexp(Pexp_apply(ghexp(Pexp_ident(array_function "Array" "get")), ["",$1; "",$4])) } | simple_expr DOT LPAREN seq_expr error { unclosed "(" 3 ")" 5 } | simple_expr DOT LBRACKET seq_expr RBRACKET { mkexp(Pexp_apply(ghexp(Pexp_ident(array_function "String" "get")), ["",$1; "",$4])) } | simple_expr DOT LBRACKET seq_expr error { unclosed "[" 3 "]" 5 } | simple_expr DOT LBRACE expr RBRACE { bigarray_get $1 $4 } | simple_expr DOT LBRACE expr_comma_list error { unclosed "{" 3 "}" 5 } | LBRACE record_expr RBRACE { let (exten, fields) = $2 in mkexp(Pexp_record(fields, exten)) } | LBRACE record_expr error { unclosed "{" 1 "}" 3 } | LBRACKETBAR expr_semi_list opt_semi BARRBRACKET { mkexp(Pexp_array(List.rev $2)) } | LBRACKETBAR expr_semi_list opt_semi error { unclosed "[|" 1 "|]" 4 } | LBRACKETBAR BARRBRACKET { mkexp(Pexp_array []) } | LBRACKET expr_semi_list opt_semi RBRACKET { reloc_exp (mktailexp (List.rev $2)) } | LBRACKET expr_semi_list opt_semi error { unclosed "[" 1 "]" 4 } | PREFIXOP simple_expr { mkexp(Pexp_apply(mkoperator $1 1, ["",$2])) } | NEW class_longident { mkexp(Pexp_new($2)) } | LBRACELESS field_expr_list opt_semi GREATERRBRACE { mkexp(Pexp_override(List.rev $2)) } | LBRACELESS field_expr_list opt_semi error { unclosed "{<" 1 ">}" 4 } | LBRACELESS GREATERRBRACE { mkexp(Pexp_override []) } | simple_expr SHARP label { mkexp(Pexp_send($1, $3)) } ; simple_labeled_expr_list: labeled_simple_expr { [$1] } | simple_labeled_expr_list labeled_simple_expr { $2 :: $1 } ; labeled_simple_expr: simple_expr %prec below_SHARP { ("", $1) } | label_expr { $1 } ; label_expr: LABEL simple_expr %prec below_SHARP { ($1, $2) } | TILDE label_ident { $2 } | QUESTION label_ident { ("?" ^ fst $2, snd $2) } | OPTLABEL simple_expr %prec below_SHARP { ("?" ^ $1, $2) } ; label_ident: LIDENT { ($1, mkexp(Pexp_ident(Lident $1))) } ; let_bindings: let_binding { [$1] } | let_bindings AND let_binding { $3 :: $1 } ; let_binding: val_ident fun_binding { ({ppat_desc = Ppat_var $1; ppat_loc = rhs_loc 1}, $2) } | pattern EQUAL seq_expr { ($1, $3) } ; fun_binding: strict_binding { $1 } | type_constraint EQUAL seq_expr { let (t, t') = $1 in ghexp(Pexp_constraint($3, t, t')) } ; strict_binding: EQUAL seq_expr { $2 } | labeled_simple_pattern fun_binding { let (l, o, p) = $1 in ghexp(Pexp_function(l, o, [p, $2])) } ; match_cases: pattern match_action { [$1, $2] } | match_cases BAR pattern match_action { ($3, $4) :: $1 } ; fun_def: match_action { $1 } | labeled_simple_pattern fun_def { let (l,o,p) = $1 in ghexp(Pexp_function(l, o, [p, $2])) } ; match_action: MINUSGREATER seq_expr { $2 } | WHEN seq_expr MINUSGREATER seq_expr { mkexp(Pexp_when($2, $4)) } ; expr_comma_list: expr_comma_list COMMA expr { $3 :: $1 } | expr COMMA expr { [$3; $1] } ; record_expr: simple_expr WITH lbl_expr_list opt_semi { (Some $1, List.rev $3) } | lbl_expr_list opt_semi { (None, List.rev $1) } ; lbl_expr_list: label_longident EQUAL expr { [$1,$3] } | lbl_expr_list SEMI label_longident EQUAL expr { ($3, $5) :: $1 } ; field_expr_list: label EQUAL expr { [$1,$3] } | field_expr_list SEMI label EQUAL expr { ($3, $5) :: $1 } ; expr_semi_list: expr { [$1] } | expr_semi_list SEMI expr { $3 :: $1 } ; type_constraint: COLON core_type { (Some $2, None) } | COLON core_type COLONGREATER core_type { (Some $2, Some $4) } | COLONGREATER core_type { (None, Some $2) } | COLON error { syntax_error() } | COLONGREATER error { syntax_error() } ; /* Patterns */ pattern: simple_pattern { $1 } | pattern AS val_ident { mkpat(Ppat_alias($1, $3)) } | pattern_comma_list %prec below_COMMA { mkpat(Ppat_tuple(List.rev $1)) } | constr_longident pattern %prec prec_constr_appl { mkpat(Ppat_construct($1, Some $2, false)) } | name_tag pattern %prec prec_constr_appl { mkpat(Ppat_variant($1, Some $2)) } | pattern COLONCOLON pattern { mkpat(Ppat_construct(Lident "::", Some(ghpat(Ppat_tuple[$1;$3])), false)) } | pattern BAR pattern { mkpat(Ppat_or($1, $3)) } ; simple_pattern: val_ident %prec below_EQUAL { mkpat(Ppat_var $1) } | UNDERSCORE { mkpat(Ppat_any) } | signed_constant { mkpat(Ppat_constant $1) } | CHAR DOTDOT CHAR { mkrangepat $1 $3 } | constr_longident { mkpat(Ppat_construct($1, None, false)) } | name_tag { mkpat(Ppat_variant($1, None)) } | SHARP type_longident { mkpat(Ppat_type $2) } | LBRACE lbl_pattern_list opt_semi RBRACE { mkpat(Ppat_record(List.rev $2)) } | LBRACE lbl_pattern_list opt_semi error { unclosed "{" 1 "}" 4 } | LBRACKET pattern_semi_list opt_semi RBRACKET { reloc_pat (mktailpat (List.rev $2)) } | LBRACKET pattern_semi_list opt_semi error { unclosed "[" 1 "]" 4 } | LBRACKETBAR pattern_semi_list opt_semi BARRBRACKET { mkpat(Ppat_array(List.rev $2)) } | LBRACKETBAR BARRBRACKET { mkpat(Ppat_array []) } | LBRACKETBAR pattern_semi_list opt_semi error { unclosed "[|" 1 "|]" 4 } | LPAREN pattern RPAREN { reloc_pat $2 } | LPAREN pattern error { unclosed "(" 1 ")" 3 } | LPAREN pattern COLON core_type RPAREN { mkpat(Ppat_constraint($2, $4)) } | LPAREN pattern COLON core_type error { unclosed "(" 1 ")" 5 } ; pattern_comma_list: pattern_comma_list COMMA pattern { $3 :: $1 } | pattern COMMA pattern { [$3; $1] } ; pattern_semi_list: pattern { [$1] } | pattern_semi_list SEMI pattern { $3 :: $1 } ; lbl_pattern_list: label_longident EQUAL pattern { [($1, $3)] } | lbl_pattern_list SEMI label_longident EQUAL pattern { ($3, $5) :: $1 } ; /* Primitive declarations */ primitive_declaration: STRING { [$1] } | STRING primitive_declaration { $1 :: $2 } ; /* Type declarations */ type_declarations: type_declaration { [$1] } | type_declarations AND type_declaration { $3 :: $1 } ; type_declaration: type_parameters LIDENT type_kind constraints { let (params, variance) = List.split $1 in let (kind, manifest) = $3 in ($2, {ptype_params = params; ptype_cstrs = List.rev $4; ptype_kind = kind; ptype_manifest = manifest; ptype_variance = variance; ptype_loc = symbol_rloc()}) } ; constraints: constraints CONSTRAINT constrain { $3 :: $1 } | /* empty */ { [] } ; type_kind: /*empty*/ { (Ptype_abstract, None) } | EQUAL core_type { (Ptype_abstract, Some $2) } | EQUAL constructor_declarations { (Ptype_variant(List.rev $2, Public), None) } | EQUAL PRIVATE constructor_declarations { (Ptype_variant(List.rev $3, Private), None) } | EQUAL private_flag BAR constructor_declarations { (Ptype_variant(List.rev $4, $2), None) } | EQUAL private_flag LBRACE label_declarations opt_semi RBRACE { (Ptype_record(List.rev $4, $2), None) } | EQUAL core_type EQUAL private_flag opt_bar constructor_declarations { (Ptype_variant(List.rev $6, $4), Some $2) } | EQUAL core_type EQUAL private_flag LBRACE label_declarations opt_semi RBRACE { (Ptype_record(List.rev $6, $4), Some $2) } ; type_parameters: /*empty*/ { [] } | type_parameter { [$1] } | LPAREN type_parameter_list RPAREN { List.rev $2 } ; type_parameter: type_variance QUOTE ident { $3, $1 } ; type_variance: /* empty */ { false, false } | PLUS { true, false } | MINUS { false, true } ; type_parameter_list: type_parameter { [$1] } | type_parameter_list COMMA type_parameter { $3 :: $1 } ; constructor_declarations: constructor_declaration { [$1] } | constructor_declarations BAR constructor_declaration { $3 :: $1 } ; constructor_declaration: constr_ident constructor_arguments { ($1, $2) } ; constructor_arguments: /*empty*/ { [] } | OF core_type_list { List.rev $2 } ; label_declarations: label_declaration { [$1] } | label_declarations SEMI label_declaration { $3 :: $1 } ; label_declaration: mutable_flag label COLON poly_type { ($2, $1, $4) } ; /* "with" constraints (additional type equations over signature components) */ with_constraints: with_constraint { [$1] } | with_constraints AND with_constraint { $3 :: $1 } ; with_constraint: TYPE type_parameters label_longident EQUAL core_type constraints { let params, variance = List.split $2 in ($3, Pwith_type {ptype_params = params; ptype_cstrs = List.rev $6; ptype_kind = Ptype_abstract; ptype_manifest = Some $5; ptype_variance = variance; ptype_loc = symbol_rloc()}) } /* used label_longident instead of type_longident to disallow functor applications in type path */ | MODULE mod_longident EQUAL mod_ext_longident { ($2, Pwith_module $4) } ; /* Polymorphic types */ typevar_list: QUOTE ident { [$2] } | typevar_list QUOTE ident { $3 :: $1 } ; poly_type: core_type { mktyp(Ptyp_poly([], $1)) } | typevar_list DOT core_type { mktyp(Ptyp_poly(List.rev $1, $3)) } ; /* Core types */ core_type: core_type2 { $1 } | core_type2 AS QUOTE ident { mktyp(Ptyp_alias($1, $4)) } ; core_type2: simple_core_type_or_tuple { $1 } | QUESTION LIDENT COLON core_type2 MINUSGREATER core_type2 { mktyp(Ptyp_arrow("?" ^ $2 , {ptyp_desc = Ptyp_constr(Lident "option", [$4]); ptyp_loc = $4.ptyp_loc}, $6)) } | OPTLABEL core_type2 MINUSGREATER core_type2 { mktyp(Ptyp_arrow("?" ^ $1 , {ptyp_desc = Ptyp_constr(Lident "option", [$2]); ptyp_loc = $2.ptyp_loc}, $4)) } | LIDENT COLON core_type2 MINUSGREATER core_type2 { mktyp(Ptyp_arrow($1, $3, $5)) } | core_type2 MINUSGREATER core_type2 { mktyp(Ptyp_arrow("", $1, $3)) } ; simple_core_type: simple_core_type2 %prec below_SHARP { $1 } | LPAREN core_type_comma_list RPAREN %prec below_SHARP { match $2 with [sty] -> sty | _ -> raise Parse_error } ; simple_core_type2: QUOTE ident { mktyp(Ptyp_var $2) } | UNDERSCORE { mktyp(Ptyp_any) } | type_longident { mktyp(Ptyp_constr($1, [])) } | simple_core_type2 type_longident { mktyp(Ptyp_constr($2, [$1])) } | LPAREN core_type_comma_list RPAREN type_longident { mktyp(Ptyp_constr($4, List.rev $2)) } | LESS meth_list GREATER { mktyp(Ptyp_object $2) } | LESS GREATER { mktyp(Ptyp_object []) } | SHARP class_longident opt_present { mktyp(Ptyp_class($2, [], $3)) } | simple_core_type2 SHARP class_longident opt_present { mktyp(Ptyp_class($3, [$1], $4)) } | LPAREN core_type_comma_list RPAREN SHARP class_longident opt_present { mktyp(Ptyp_class($5, List.rev $2, $6)) } | LBRACKET tag_field RBRACKET { mktyp(Ptyp_variant([$2], true, None)) } | LBRACKET BAR row_field_list RBRACKET { mktyp(Ptyp_variant(List.rev $3, true, None)) } | LBRACKET row_field BAR row_field_list RBRACKET { mktyp(Ptyp_variant($2 :: List.rev $4, true, None)) } | LBRACKETGREATER opt_bar row_field_list RBRACKET { mktyp(Ptyp_variant(List.rev $3, false, None)) } | LBRACKETGREATER RBRACKET { mktyp(Ptyp_variant([], false, None)) } | LBRACKETLESS opt_bar row_field_list RBRACKET { mktyp(Ptyp_variant(List.rev $3, true, Some [])) } | LBRACKETLESS opt_bar row_field_list GREATER name_tag_list RBRACKET { mktyp(Ptyp_variant(List.rev $3, true, Some (List.rev $5))) } ; row_field_list: row_field { [$1] } | row_field_list BAR row_field { $3 :: $1 } ; row_field: tag_field { $1 } | simple_core_type2 { Rinherit $1 } ; tag_field: name_tag OF opt_ampersand amper_type_list { Rtag ($1, $3, List.rev $4) } | name_tag { Rtag ($1, true, []) } ; opt_ampersand: AMPERSAND { true } | /* empty */ { false } ; amper_type_list: core_type { [$1] } | amper_type_list AMPERSAND core_type { $3 :: $1 } ; opt_present: LBRACKETGREATER name_tag_list RBRACKET { List.rev $2 } | /* empty */ { [] } ; name_tag_list: name_tag { [$1] } | name_tag_list name_tag { $2 :: $1 } ; simple_core_type_or_tuple: simple_core_type { $1 } | simple_core_type STAR core_type_list { mktyp(Ptyp_tuple($1 :: List.rev $3)) } ; core_type_comma_list: core_type { [$1] } | core_type_comma_list COMMA core_type { $3 :: $1 } ; core_type_list: simple_core_type { [$1] } | core_type_list STAR simple_core_type { $3 :: $1 } ; meth_list: field SEMI meth_list { $1 :: $3 } | field opt_semi { [$1] } | DOTDOT { [mkfield Pfield_var] } ; field: label COLON poly_type { mkfield(Pfield($1, $3)) } ; label: LIDENT { $1 } ; /* Constants */ constant: INT { Const_int $1 } | CHAR { Const_char $1 } | STRING { Const_string $1 } | FLOAT { Const_float $1 } | INT32 { Const_int32 $1 } | INT64 { Const_int64 $1 } | NATIVEINT { Const_nativeint $1 } ; signed_constant: constant { $1 } | MINUS INT { Const_int(- $2) } | MINUS FLOAT { Const_float("-" ^ $2) } | MINUS INT32 { Const_int32(Int32.neg $2) } | MINUS INT64 { Const_int64(Int64.neg $2) } | MINUS NATIVEINT { Const_nativeint(Nativeint.neg $2) } ; /* Identifiers and long identifiers */ ident: UIDENT { $1 } | LIDENT { $1 } ; val_ident: LIDENT { $1 } | LPAREN operator RPAREN { $2 } ; val_ident_colon: LIDENT COLON { $1 } | LPAREN operator RPAREN COLON { $2 } | LABEL { $1 } ; operator: PREFIXOP { $1 } | INFIXOP0 { $1 } | INFIXOP1 { $1 } | INFIXOP2 { $1 } | INFIXOP3 { $1 } | INFIXOP4 { $1 } | PLUS { "+" } | MINUS { "-" } | MINUSDOT { "-." } | STAR { "*" } | EQUAL { "=" } | LESS { "<" } | GREATER { ">" } | OR { "or" } | BARBAR { "||" } | AMPERSAND { "&" } | AMPERAMPER { "&&" } | COLONEQUAL { ":=" } ; constr_ident: UIDENT { $1 } /* | LBRACKET RBRACKET { "[]" } */ | LPAREN RPAREN { "()" } | COLONCOLON { "::" } | FALSE { "false" } | TRUE { "true" } ; val_longident: val_ident { Lident $1 } | mod_longident DOT val_ident { Ldot($1, $3) } ; constr_longident: mod_longident %prec below_DOT { $1 } | LBRACKET RBRACKET { Lident "[]" } | LPAREN RPAREN { Lident "()" } | FALSE { Lident "false" } | TRUE { Lident "true" } ; label_longident: LIDENT { Lident $1 } | mod_longident DOT LIDENT { Ldot($1, $3) } ; type_longident: LIDENT { Lident $1 } | mod_ext_longident DOT LIDENT { Ldot($1, $3) } ; mod_longident: UIDENT { Lident $1 } | mod_longident DOT UIDENT { Ldot($1, $3) } ; mod_ext_longident: UIDENT { Lident $1 } | mod_ext_longident DOT UIDENT { Ldot($1, $3) } | mod_ext_longident LPAREN mod_ext_longident RPAREN { Lapply($1, $3) } ; mty_longident: ident { Lident $1 } | mod_ext_longident DOT ident { Ldot($1, $3) } ; clty_longident: LIDENT { Lident $1 } | mod_ext_longident DOT LIDENT { Ldot($1, $3) } ; class_longident: LIDENT { Lident $1 } | mod_longident DOT LIDENT { Ldot($1, $3) } ; /* Toplevel directives */ toplevel_directive: SHARP ident { Ptop_dir($2, Pdir_none) } | SHARP ident STRING { Ptop_dir($2, Pdir_string $3) } | SHARP ident INT { Ptop_dir($2, Pdir_int $3) } | SHARP ident val_longident { Ptop_dir($2, Pdir_ident $3) } | SHARP ident FALSE { Ptop_dir($2, Pdir_bool false) } | SHARP ident TRUE { Ptop_dir($2, Pdir_bool true) } ; /* Miscellaneous */ name_tag: BACKQUOTE ident { $2 } ; rec_flag: /* empty */ { Nonrecursive } | REC { Recursive } ; direction_flag: TO { Upto } | DOWNTO { Downto } ; private_flag: /* empty */ { Public } | PRIVATE { Private } ; mutable_flag: /* empty */ { Immutable } | MUTABLE { Mutable } ; virtual_flag: /* empty */ { Concrete } | VIRTUAL { Virtual } ; opt_bar: /* empty */ { () } | BAR { () } ; opt_semi: | /* empty */ { () } | SEMI { () } ; subtractive: | MINUS { "-" } | MINUSDOT { "-." } ; %% ocamlweb-1.41/ocaml-parser/lexer.mli0000755000246300004300000000241413422556306017002 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* The lexical analyzer *) val token: Lexing.lexbuf -> Parser.token val skip_sharp_bang: Lexing.lexbuf -> unit type error = | Illegal_character of char | Illegal_escape of string | Unterminated_comment | Unterminated_string | Unterminated_string_in_comment | Keyword_as_label of string | Literal_overflow of string ;; exception Error of error * Location.t open Format val report_error: formatter -> error -> unit val in_comment : unit -> bool;; ocamlweb-1.41/ocaml-parser/lexer.mll0000755000246300004300000003471213422556307017014 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* The lexer definition *) { open Lexing open Misc open Parser type error = | Illegal_character of char | Illegal_escape of string | Unterminated_comment | Unterminated_string | Unterminated_string_in_comment | Keyword_as_label of string | Literal_overflow of string ;; exception Error of error * Location.t;; (* The table of keywords *) let keyword_table = create_hashtable 149 [ "and", AND; "as", AS; "assert", ASSERT; "begin", BEGIN; "class", CLASS; "constraint", CONSTRAINT; "do", DO; "done", DONE; "downto", DOWNTO; "else", ELSE; "end", END; "exception", EXCEPTION; "external", EXTERNAL; "false", FALSE; "for", FOR; "fun", FUN; "function", FUNCTION; "functor", FUNCTOR; "if", IF; "in", IN; "include", INCLUDE; "inherit", INHERIT; "initializer", INITIALIZER; "lazy", LAZY; "let", LET; "match", MATCH; "method", METHOD; "module", MODULE; "mutable", MUTABLE; "new", NEW; "object", OBJECT; "of", OF; "open", OPEN; "or", OR; (* "parser", PARSER; *) "private", PRIVATE; "rec", REC; "sig", SIG; "struct", STRUCT; "then", THEN; "to", TO; "true", TRUE; "try", TRY; "type", TYPE; "val", VAL; "virtual", VIRTUAL; "when", WHEN; "while", WHILE; "with", WITH; "mod", INFIXOP3("mod"); "land", INFIXOP3("land"); "lor", INFIXOP3("lor"); "lxor", INFIXOP3("lxor"); "lsl", INFIXOP4("lsl"); "lsr", INFIXOP4("lsr"); "asr", INFIXOP4("asr") ] (* To buffer string literals *) let string_buffer = Buffer.create 256 let reset_string_buffer () = Buffer.reset string_buffer let store_string_char c = Buffer.add_char string_buffer c let get_stored_string () = Buffer.contents string_buffer (* To store the position of the beginning of a string and comment *) let string_start_loc = ref Location.none;; let comment_start_loc = ref [];; let in_comment () = !comment_start_loc <> [];; (* To translate escape sequences *) let char_for_backslash = function | 'n' -> '\010' | 'r' -> '\013' | 'b' -> '\008' | 't' -> '\009' | c -> c let char_for_decimal_code lexbuf i = let c = 100 * (Char.code(Lexing.lexeme_char lexbuf i) - 48) + 10 * (Char.code(Lexing.lexeme_char lexbuf (i+1)) - 48) + (Char.code(Lexing.lexeme_char lexbuf (i+2)) - 48) in if (c < 0 || c > 255) && not (in_comment ()) then raise (Error(Illegal_escape (Lexing.lexeme lexbuf), Location.curr lexbuf)) else Char.chr c let char_for_hexadecimal_code lexbuf i = let d1 = Char.code (Lexing.lexeme_char lexbuf i) in let val1 = if d1 >= 97 then d1 - 87 else if d1 >= 65 then d1 - 55 else d1 - 48 in let d2 = Char.code (Lexing.lexeme_char lexbuf (i+1)) in let val2 = if d2 >= 97 then d2 - 87 else if d2 >= 65 then d2 - 55 else d2 - 48 in Char.chr (val1 * 16 + val2) (* Remove underscores from float literals *) let remove_underscores s = let l = String.length s in let b = Buffer.create l in for i = 0 to l - 1 do match s.[i] with | '_' -> () | c -> Buffer.add_char b c done; Buffer.contents b (* Update the current location with file name and line number. *) let update_loc lexbuf file line absolute chars = let pos = lexbuf.lex_curr_p in let new_file = match file with | None -> pos.pos_fname | Some s -> s in lexbuf.lex_curr_p <- { pos with pos_fname = new_file; pos_lnum = if absolute then line else pos.pos_lnum + line; pos_bol = pos.pos_cnum - chars; } ;; (* Error report *) open Format let report_error ppf = function | Illegal_character c -> fprintf ppf "Illegal character (%s)" (Char.escaped c) | Illegal_escape s -> fprintf ppf "Illegal backslash escape in string or character (%s)" s | Unterminated_comment -> fprintf ppf "Comment not terminated" | Unterminated_string -> fprintf ppf "String literal not terminated" | Unterminated_string_in_comment -> fprintf ppf "This comment contains an unterminated string literal" | Keyword_as_label kwd -> fprintf ppf "`%s' is a keyword, it cannot be used as label name" kwd | Literal_overflow ty -> fprintf ppf "Integer literal exceeds the range of representable integers of type %s" ty ;; } let newline = ('\010' | '\013' | "\013\010") let blank = [' ' '\009' '\012'] let lowercase = ['a'-'z' '\223'-'\246' '\248'-'\255' '_'] let uppercase = ['A'-'Z' '\192'-'\214' '\216'-'\222'] let identchar = ['A'-'Z' 'a'-'z' '_' '\192'-'\214' '\216'-'\246' '\248'-'\255' '\'' '0'-'9'] let symbolchar = ['!' '$' '%' '&' '*' '+' '-' '.' '/' ':' '<' '=' '>' '?' '@' '^' '|' '~'] let decimal_literal = ['0'-'9'] ['0'-'9' '_']* let hex_literal = '0' ['x' 'X'] ['0'-'9' 'A'-'F' 'a'-'f']['0'-'9' 'A'-'F' 'a'-'f' '_']* let oct_literal = '0' ['o' 'O'] ['0'-'7'] ['0'-'7' '_']* let bin_literal = '0' ['b' 'B'] ['0'-'1'] ['0'-'1' '_']* let int_literal = decimal_literal | hex_literal | oct_literal | bin_literal let float_literal = ['0'-'9'] ['0'-'9' '_']* ('.' ['0'-'9' '_']* )? (['e' 'E'] ['+' '-']? ['0'-'9'] ['0'-'9' '_']*)? rule token = parse | newline { update_loc lexbuf None 1 false 0; token lexbuf } | blank + { token lexbuf } | "_" { UNDERSCORE } | "~" { TILDE } | "~" lowercase identchar * ':' { let s = Lexing.lexeme lexbuf in let name = String.sub s 1 (String.length s - 2) in if Hashtbl.mem keyword_table name then raise (Error(Keyword_as_label name, Location.curr lexbuf)); LABEL name } | "?" { QUESTION } | "??" { QUESTIONQUESTION } | "?" lowercase identchar * ':' { let s = Lexing.lexeme lexbuf in let name = String.sub s 1 (String.length s - 2) in if Hashtbl.mem keyword_table name then raise (Error(Keyword_as_label name, Location.curr lexbuf)); OPTLABEL name } | lowercase identchar * { let s = Lexing.lexeme lexbuf in try Hashtbl.find keyword_table s with Not_found -> LIDENT s } | uppercase identchar * { UIDENT(Lexing.lexeme lexbuf) } (* No capitalized keywords *) | int_literal { try INT (int_of_string(Lexing.lexeme lexbuf)) with Failure _ -> raise (Error(Literal_overflow "int", Location.curr lexbuf)) } | float_literal { FLOAT (remove_underscores(Lexing.lexeme lexbuf)) } | int_literal "l" { let s = Lexing.lexeme lexbuf in try INT32 (Int32.of_string(String.sub s 0 (String.length s - 1))) with Failure _ -> raise (Error(Literal_overflow "int32", Location.curr lexbuf)) } | int_literal "L" { let s = Lexing.lexeme lexbuf in try INT64 (Int64.of_string(String.sub s 0 (String.length s - 1))) with Failure _ -> raise (Error(Literal_overflow "int64", Location.curr lexbuf)) } | int_literal "n" { let s = Lexing.lexeme lexbuf in try NATIVEINT (Nativeint.of_string(String.sub s 0 (String.length s - 1))) with Failure _ -> raise (Error(Literal_overflow "nativeint", Location.curr lexbuf)) } | "\"" { reset_string_buffer(); let string_start = lexbuf.lex_start_p in string_start_loc := Location.curr lexbuf; string lexbuf; lexbuf.lex_start_p <- string_start; STRING (get_stored_string()) } | "'" newline "'" { update_loc lexbuf None 1 false 1; CHAR (Lexing.lexeme_char lexbuf 1) } | "'" [^ '\\' '\'' '\010' '\013'] "'" { CHAR(Lexing.lexeme_char lexbuf 1) } | "'\\" ['\\' '\'' '"' 'n' 't' 'b' 'r'] "'" { CHAR(char_for_backslash (Lexing.lexeme_char lexbuf 2)) } | "'\\" ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { CHAR(char_for_decimal_code lexbuf 2) } | "'\\" 'x' ['0'-'9' 'a'-'f' 'A'-'F'] ['0'-'9' 'a'-'f' 'A'-'F'] "'" { CHAR(char_for_hexadecimal_code lexbuf 3) } | "'\\" _ { let l = Lexing.lexeme lexbuf in let esc = String.sub l 1 (String.length l - 1) in raise (Error(Illegal_escape esc, Location.curr lexbuf)) } | "(*" { comment_start_loc := [Location.curr lexbuf]; comment lexbuf; token lexbuf } | "(*)" { let loc = Location.curr lexbuf in Location.prerr_warning loc (Warnings.Comment "the start of a comment"); comment_start_loc := [Location.curr lexbuf]; comment lexbuf; token lexbuf } | "*)" { let loc = Location.curr lexbuf in let warn = Warnings.Comment "not the end of a comment" in Location.prerr_warning loc warn; lexbuf.Lexing.lex_curr_pos <- lexbuf.Lexing.lex_curr_pos - 1; let curpos = lexbuf.lex_curr_p in lexbuf.lex_curr_p <- { curpos with pos_cnum = curpos.pos_cnum - 1 }; STAR } | "#" [' ' '\t']* (['0'-'9']+ as num) [' ' '\t']* ("\"" ([^ '\010' '\013' '"' ] * as name) "\"")? [^ '\010' '\013'] * newline { update_loc lexbuf name (int_of_string num) true 0; token lexbuf } | "#" { SHARP } | "&" { AMPERSAND } | "&&" { AMPERAMPER } | "`" { BACKQUOTE } | "'" { QUOTE } | "(" { LPAREN } | ")" { RPAREN } | "*" { STAR } | "," { COMMA } | "->" { MINUSGREATER } | "." { DOT } | ".." { DOTDOT } | ":" { COLON } | "::" { COLONCOLON } | ":=" { COLONEQUAL } | ":>" { COLONGREATER } | ";" { SEMI } | ";;" { SEMISEMI } | "<" { LESS } | "<-" { LESSMINUS } | "=" { EQUAL } | "[" { LBRACKET } | "[|" { LBRACKETBAR } | "[<" { LBRACKETLESS } | "[>" { LBRACKETGREATER } | "]" { RBRACKET } | "{" { LBRACE } | "{<" { LBRACELESS } | "|" { BAR } | "||" { BARBAR } | "|]" { BARRBRACKET } | ">" { GREATER } | ">]" { GREATERRBRACKET } | "}" { RBRACE } | ">}" { GREATERRBRACE } | "!=" { INFIXOP0 "!=" } | "+" { PLUS } | "-" { MINUS } | "-." { MINUSDOT } | "!" symbolchar * { PREFIXOP(Lexing.lexeme lexbuf) } | ['~' '?'] symbolchar + { PREFIXOP(Lexing.lexeme lexbuf) } | ['=' '<' '>' '|' '&' '$'] symbolchar * { INFIXOP0(Lexing.lexeme lexbuf) } | ['@' '^'] symbolchar * { INFIXOP1(Lexing.lexeme lexbuf) } | ['+' '-'] symbolchar * { INFIXOP2(Lexing.lexeme lexbuf) } | "**" symbolchar * { INFIXOP4(Lexing.lexeme lexbuf) } | ['*' '/' '%'] symbolchar * { INFIXOP3(Lexing.lexeme lexbuf) } | eof { EOF } | _ { raise (Error(Illegal_character (Lexing.lexeme_char lexbuf 0), Location.curr lexbuf)) } and comment = parse "(*" { comment_start_loc := (Location.curr lexbuf) :: !comment_start_loc; comment lexbuf; } | "*)" { match !comment_start_loc with | [] -> assert false | [x] -> comment_start_loc := []; | _ :: l -> comment_start_loc := l; comment lexbuf; } | "\"" { reset_string_buffer(); string_start_loc := Location.curr lexbuf; begin try string lexbuf with Error (Unterminated_string, _) -> match !comment_start_loc with | [] -> assert false | loc :: _ -> comment_start_loc := []; raise (Error (Unterminated_string_in_comment, loc)) end; reset_string_buffer (); comment lexbuf } | "''" { comment lexbuf } | "'" newline "'" { update_loc lexbuf None 1 false 1; comment lexbuf } | "'" [^ '\\' '\'' '\010' '\013' ] "'" { comment lexbuf } | "'\\" ['\\' '"' '\'' 'n' 't' 'b' 'r'] "'" { comment lexbuf } | "'\\" ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { comment lexbuf } | "'\\" 'x' ['0'-'9' 'a'-'f' 'A'-'F'] ['0'-'9' 'a'-'f' 'A'-'F'] "'" { comment lexbuf } | eof { match !comment_start_loc with | [] -> assert false | loc :: _ -> comment_start_loc := []; raise (Error (Unterminated_comment, loc)) } | newline { update_loc lexbuf None 1 false 0; comment lexbuf } | _ { comment lexbuf } and string = parse '"' { () } | '\\' newline ([' ' '\t'] * as space) { update_loc lexbuf None 1 false (String.length space); string lexbuf } | '\\' ['\\' '\'' '"' 'n' 't' 'b' 'r'] { store_string_char(char_for_backslash(Lexing.lexeme_char lexbuf 1)); string lexbuf } | '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] { store_string_char(char_for_decimal_code lexbuf 1); string lexbuf } | '\\' 'x' ['0'-'9' 'a'-'f' 'A'-'F'] ['0'-'9' 'a'-'f' 'A'-'F'] { store_string_char(char_for_hexadecimal_code lexbuf 2); string lexbuf } | '\\' _ { if in_comment () then string lexbuf else begin (* Should be an error, but we are very lax. raise (Error (Illegal_escape (Lexing.lexeme lexbuf), Location.curr lexbuf)) *) let loc = Location.curr lexbuf in let warn = Warnings.Other "Illegal backslash escape in string" in Location.prerr_warning loc warn; store_string_char (Lexing.lexeme_char lexbuf 0); store_string_char (Lexing.lexeme_char lexbuf 1); string lexbuf end } | newline { update_loc lexbuf None 1 false 0; let s = Lexing.lexeme lexbuf in for i = 0 to String.length s - 1 do store_string_char s.[i]; done; string lexbuf } | eof { raise (Error (Unterminated_string, !string_start_loc)) } | _ { store_string_char(Lexing.lexeme_char lexbuf 0); string lexbuf } and skip_sharp_bang = parse | "#!" [^ '\n']* '\n' [^ '\n']* "\n!#\n" { update_loc lexbuf None 3 false 0 } | "#!" [^ '\n']* '\n' { update_loc lexbuf None 1 false 0 } | "" { () } ocamlweb-1.41/ocaml-parser/parse.mli0000755000246300004300000000211513422556307016774 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Entry points in the parser *) val implementation : Lexing.lexbuf -> Parsetree.structure val interface : Lexing.lexbuf -> Parsetree.signature val toplevel_phrase : Lexing.lexbuf -> Parsetree.toplevel_phrase val use_file : Lexing.lexbuf -> Parsetree.toplevel_phrase list ocamlweb-1.41/ocaml-parser/parse.ml0000755000246300004300000000463013422556307016627 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* Entry points in the parser *) open Location (* Skip tokens to the end of the phrase *) let rec skip_phrase lexbuf = try match Lexer.token lexbuf with Parser.SEMISEMI | Parser.EOF -> () | _ -> skip_phrase lexbuf with | Lexer.Error (Lexer.Unterminated_comment, _) -> () | Lexer.Error (Lexer.Unterminated_string, _) -> () | Lexer.Error (Lexer.Unterminated_string_in_comment, _) -> () | Lexer.Error (Lexer.Illegal_character _, _) -> skip_phrase lexbuf ;; let maybe_skip_phrase lexbuf = if Parsing.is_current_lookahead Parser.SEMISEMI || Parsing.is_current_lookahead Parser.EOF then () else skip_phrase lexbuf let wrap parsing_fun lexbuf = try let ast = parsing_fun Lexer.token lexbuf in Parsing.clear_parser(); ast with | Lexer.Error(Lexer.Unterminated_comment, _) as err -> raise err | Lexer.Error(Lexer.Unterminated_string, _) as err -> raise err | Lexer.Error(Lexer.Unterminated_string_in_comment, _) as err -> raise err | Lexer.Error(Lexer.Illegal_character _, _) as err -> if !Location.input_name = "" then skip_phrase lexbuf; raise err | Syntaxerr.Error _ as err -> if !Location.input_name = "" then maybe_skip_phrase lexbuf; raise err | Parsing.Parse_error | Syntaxerr.Escape_error -> let loc = Location.curr lexbuf in if !Location.input_name = "" then maybe_skip_phrase lexbuf; raise(Syntaxerr.Error(Syntaxerr.Other loc)) ;; let implementation = wrap Parser.implementation and interface = wrap Parser.interface and toplevel_phrase = wrap Parser.toplevel_phrase and use_file = wrap Parser.use_file ocamlweb-1.41/ocaml-parser/README0000644000246300004300000000043213422556307016034 0ustar filliatrvals This directory contains the ocaml parser, copied `as is' from the ocaml sources. All this code is copyright 1996 "Institut National de Recherche en Informatique et en Automatique" and distributed under the terms of the Q Public License version 1.0 (enclosed in the file LICENSE). ocamlweb-1.41/ocaml-parser/LICENSE0000755000246300004300000007553313422556307016202 0ustar filliatrvalsIn the following, "the Library" refers to all files marked "Copyright INRIA" in the following directories and their sub-directories: asmrun, byterun, config, maccaml, otherlibs, stdlib, win32caml and "the Compiler" refers to all files marked "Copyright INRIA" in the other directories and their sub-directories. The Compiler is distributed under the terms of the Q Public License version 1.0 (included below). The Library is distributed under the terms of the GNU Library General Public License version 2 (included below). As a special exception to the GNU Library General Public License, you may link, statically or dynamically, a "work that uses the Library" with a publicly distributed version of the Library to produce an executable file containing portions of the Library, and distribute that executable file under terms of your choice, without any of the additional requirements listed in clause 6 of the GNU Library General Public License. By "a publicly distributed version of the Library", we mean either the unmodified Library as distributed by INRIA, or a modified version of the Library that is distributed under the conditions defined in clause 3 of the GNU Library General Public License. This exception does not however invalidate any other reasons why the executable file might be covered by the GNU Library General Public License. ---------------------------------------------------------------------- THE Q PUBLIC LICENSE version 1.0 Copyright (C) 1999 Troll Tech AS, Norway. Everyone is permitted to copy and distribute this license document. The intent of this license is to establish freedom to share and change the software regulated by this license under the open source model. This license applies to any software containing a notice placed by the copyright holder saying that it may be distributed under the terms of the Q Public License version 1.0. Such software is herein referred to as the Software. This license covers modification and distribution of the Software, use of third-party application programs based on the Software, and development of free software which uses the Software. Granted Rights 1. You are granted the non-exclusive rights set forth in this license provided you agree to and comply with any and all conditions in this license. Whole or partial distribution of the Software, or software items that link with the Software, in any form signifies acceptance of this license. 2. You may copy and distribute the Software in unmodified form provided that the entire package, including - but not restricted to - copyright, trademark notices and disclaimers, as released by the initial developer of the Software, is distributed. 3. You may make modifications to the Software and distribute your modifications, in a form that is separate from the Software, such as patches. The following restrictions apply to modifications: a. Modifications must not alter or remove any copyright notices in the Software. b. When modifications to the Software are released under this license, a non-exclusive royalty-free right is granted to the initial developer of the Software to distribute your modification in future versions of the Software provided such versions remain available under these terms in addition to any other license(s) of the initial developer. 4. You may distribute machine-executable forms of the Software or machine-executable forms of modified versions of the Software, provided that you meet these restrictions: a. You must include this license document in the distribution. b. You must ensure that all recipients of the machine-executable forms are also able to receive the complete machine-readable source code to the distributed Software, including all modifications, without any charge beyond the costs of data transfer, and place prominent notices in the distribution explaining this. c. You must ensure that all modifications included in the machine-executable forms are available under the terms of this license. 5. You may use the original or modified versions of the Software to compile, link and run application programs legally developed by you or by others. 6. You may develop application programs, reusable components and other software items that link with the original or modified versions of the Software. These items, when distributed, are subject to the following requirements: a. You must ensure that all recipients of machine-executable forms of these items are also able to receive and use the complete machine-readable source code to the items without any charge beyond the costs of data transfer. b. You must explicitly license all recipients of your items to use and re-distribute original and modified versions of the items in both machine-executable and source code forms. The recipients must be able to do so without any charges whatsoever, and they must be able to re-distribute to anyone they choose. c. If the items are not available to the general public, and the initial developer of the Software requests a copy of the items, then you must supply one. Limitations of Liability In no event shall the initial developers or copyright holders be liable for any damages whatsoever, including - but not restricted to - lost revenue or profits or other direct, indirect, special, incidental or consequential damages, even if they have been advised of the possibility of such damages, except to the extent invariable law, if any, provides otherwise. No Warranty The Software and this license document are provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. Choice of Law This license is governed by the Laws of France. Disputes shall be settled by the Court of Versailles. ---------------------------------------------------------------------- GNU LIBRARY GENERAL PUBLIC LICENSE Version 2, June 1991 Copyright (C) 1991 Free Software Foundation, Inc. 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. [This is the first released version of the library GPL. It is numbered 2 because it goes with version 2 of the ordinary GPL.] Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public Licenses are intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This license, the Library General Public License, applies to some specially designated Free Software Foundation software, and to any other libraries whose authors decide to use it. You can use it for your libraries, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for this service if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs; and that you know you can do these things. To protect your rights, we need to make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights. These restrictions translate to certain responsibilities for you if you distribute copies of the library, or if you modify it. For example, if you distribute copies of the library, whether gratis or for a fee, you must give the recipients all the rights that we gave you. You must make sure that they, too, receive or can get the source code. If you link a program with the library, you must provide complete object files to the recipients so that they can relink them with the library, after making changes to the library and recompiling it. And you must show them these terms so they know their rights. Our method of protecting your rights has two steps: (1) copyright the library, and (2) offer you this license which gives you legal permission to copy, distribute and/or modify the library. Also, for each distributor's protection, we want to make certain that everyone understands that there is no warranty for this free library. If the library is modified by someone else and passed on, we want its recipients to know that what they have is not the original version, so that any problems introduced by others will not reflect on the original authors' reputations. Finally, any free program is threatened constantly by software patents. We wish to avoid the danger that companies distributing free software will individually obtain patent licenses, thus in effect transforming the program into proprietary software. To prevent this, we have made it clear that any patent must be licensed for everyone's free use or not licensed at all. Most GNU software, including some libraries, is covered by the ordinary GNU General Public License, which was designed for utility programs. This license, the GNU Library General Public License, applies to certain designated libraries. This license is quite different from the ordinary one; be sure to read it in full, and don't assume that anything in it is the same as in the ordinary license. The reason we have a separate public license for some libraries is that they blur the distinction we usually make between modifying or adding to a program and simply using it. Linking a program with a library, without changing the library, is in some sense simply using the library, and is analogous to running a utility program or application program. However, in a textual and legal sense, the linked executable is a combined work, a derivative of the original library, and the ordinary General Public License treats it as such. Because of this blurred distinction, using the ordinary General Public License for libraries did not effectively promote software sharing, because most developers did not use the libraries. We concluded that weaker conditions might promote sharing better. However, unrestricted linking of non-free programs would deprive the users of those programs of all benefit from the free status of the libraries themselves. This Library General Public License is intended to permit developers of non-free programs to use free libraries, while preserving your freedom as a user of such programs to change the free libraries that are incorporated in them. (We have not seen how to achieve this as regards changes in header files, but we have achieved it as regards changes in the actual functions of the Library.) The hope is that this will lead to faster development of free libraries. The precise terms and conditions for copying, distribution and modification follow. Pay close attention to the difference between a "work based on the library" and a "work that uses the library". The former contains code derived from the library, while the latter only works together with the library. Note that it is possible for a library to be covered by the ordinary General Public License rather than by this special one. GNU LIBRARY GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License Agreement applies to any software library which contains a notice placed by the copyright holder or other authorized party saying it may be distributed under the terms of this Library General Public License (also called "this License"). Each licensee is addressed as "you". A "library" means a collection of software functions and/or data prepared so as to be conveniently linked with application programs (which use some of those functions and data) to form executables. The "Library", below, refers to any such software library or work which has been distributed under these terms. A "work based on the Library" means either the Library or any derivative work under copyright law: that is to say, a work containing the Library or a portion of it, either verbatim or with modifications and/or translated straightforwardly into another language. (Hereinafter, translation is included without limitation in the term "modification".) "Source code" for a work means the preferred form of the work for making modifications to it. For a library, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the library. Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running a program using the Library is not restricted, and output from such a program is covered only if its contents constitute a work based on the Library (independent of the use of the Library in a tool for writing it). Whether that is true depends on what the Library does and what the program that uses the Library does. 1. You may copy and distribute verbatim copies of the Library's complete source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and distribute a copy of this License along with the Library. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Library or any portion of it, thus forming a work based on the Library, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) The modified work must itself be a software library. b) You must cause the files modified to carry prominent notices stating that you changed the files and the date of any change. c) You must cause the whole of the work to be licensed at no charge to all third parties under the terms of this License. d) If a facility in the modified Library refers to a function or a table of data to be supplied by an application program that uses the facility, other than as an argument passed when the facility is invoked, then you must make a good faith effort to ensure that, in the event an application does not supply such function or table, the facility still operates, and performs whatever part of its purpose remains meaningful. (For example, a function in a library to compute square roots has a purpose that is entirely well-defined independent of the application. Therefore, Subsection 2d requires that any application-supplied function or table used by this function must be optional: if the application does not supply it, the square root function must still compute square roots.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Library, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Library, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Library. In addition, mere aggregation of another work not based on the Library with the Library (or with a work based on the Library) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may opt to apply the terms of the ordinary GNU General Public License instead of this License to a given copy of the Library. To do this, you must alter all the notices that refer to this License, so that they refer to the ordinary GNU General Public License, version 2, instead of to this License. (If a newer version than version 2 of the ordinary GNU General Public License has appeared, then you can specify that version instead if you wish.) Do not make any other change in these notices. Once this change is made in a given copy, it is irreversible for that copy, so the ordinary GNU General Public License applies to all subsequent copies and derivative works made from that copy. This option is useful when you wish to copy part of the code of the Library into a program that is not a library. 4. You may copy and distribute the Library (or a portion or derivative of it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange. If distribution of object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place satisfies the requirement to distribute the source code, even though third parties are not compelled to copy the source along with the object code. 5. A program that contains no derivative of any portion of the Library, but is designed to work with the Library by being compiled or linked with it, is called a "work that uses the Library". Such a work, in isolation, is not a derivative work of the Library, and therefore falls outside the scope of this License. However, linking a "work that uses the Library" with the Library creates an executable that is a derivative of the Library (because it contains portions of the Library), rather than a "work that uses the library". The executable is therefore covered by this License. Section 6 states terms for distribution of such executables. When a "work that uses the Library" uses material from a header file that is part of the Library, the object code for the work may be a derivative work of the Library even though the source code is not. Whether this is true is especially significant if the work can be linked without the Library, or if the work is itself a library. The threshold for this to be true is not precisely defined by law. If such an object file uses only numerical parameters, data structure layouts and accessors, and small macros and small inline functions (ten lines or less in length), then the use of the object file is unrestricted, regardless of whether it is legally a derivative work. (Executables containing this object code plus portions of the Library will still fall under Section 6.) Otherwise, if the work is a derivative of the Library, you may distribute the object code for the work under the terms of Section 6. Any executables containing that work also fall under Section 6, whether or not they are linked directly with the Library itself. 6. As an exception to the Sections above, you may also compile or link a "work that uses the Library" with the Library to produce a work containing portions of the Library, and distribute that work under terms of your choice, provided that the terms permit modification of the work for the customer's own use and reverse engineering for debugging such modifications. You must give prominent notice with each copy of the work that the Library is used in it and that the Library and its use are covered by this License. You must supply a copy of this License. If the work during execution displays copyright notices, you must include the copyright notice for the Library among them, as well as a reference directing the user to the copy of this License. Also, you must do one of these things: a) Accompany the work with the complete corresponding machine-readable source code for the Library including whatever changes were used in the work (which must be distributed under Sections 1 and 2 above); and, if the work is an executable linked with the Library, with the complete machine-readable "work that uses the Library", as object code and/or source code, so that the user can modify the Library and then relink to produce a modified executable containing the modified Library. (It is understood that the user who changes the contents of definitions files in the Library will not necessarily be able to recompile the application to use the modified definitions.) b) Accompany the work with a written offer, valid for at least three years, to give the same user the materials specified in Subsection 6a, above, for a charge no more than the cost of performing this distribution. c) If distribution of the work is made by offering access to copy from a designated place, offer equivalent access to copy the above specified materials from the same place. d) Verify that the user has already received a copy of these materials or that you have already sent this user a copy. For an executable, the required form of the "work that uses the Library" must include any data and utility programs needed for reproducing the executable from it. However, as a special exception, the source code distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. It may happen that this requirement contradicts the license restrictions of other proprietary libraries that do not normally accompany the operating system. Such a contradiction means you cannot use both them and the Library together in an executable that you distribute. 7. You may place library facilities that are a work based on the Library side-by-side in a single library together with other library facilities not covered by this License, and distribute such a combined library, provided that the separate distribution of the work based on the Library and of the other library facilities is otherwise permitted, and provided that you do these two things: a) Accompany the combined library with a copy of the same work based on the Library, uncombined with any other library facilities. This must be distributed under the terms of the Sections above. b) Give prominent notice with the combined library of the fact that part of it is a work based on the Library, and explaining where to find the accompanying uncombined form of the same work. 8. You may not copy, modify, sublicense, link with, or distribute the Library except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense, link with, or distribute the Library is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 9. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Library or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Library (or any work based on the Library), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Library or works based on it. 10. Each time you redistribute the Library (or any work based on the Library), the recipient automatically receives a license from the original licensor to copy, distribute, link with or modify the Library subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties to this License. 11. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Library at all. For example, if a patent license would not permit royalty-free redistribution of the Library by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Library. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply, and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 12. If the distribution and/or use of the Library is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Library under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 13. The Free Software Foundation may publish revised and/or new versions of the Library General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Library specifies a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Library does not specify a license version number, you may choose any version ever published by the Free Software Foundation. 14. If you wish to incorporate parts of the Library into other free programs whose distribution conditions are incompatible with these, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. END OF TERMS AND CONDITIONS Appendix: How to Apply These Terms to Your New Libraries If you develop a new library, and you want it to be of the greatest possible use to the public, we recommend making it free software that everyone can redistribute and change. You can do so by permitting redistribution under these terms (or, alternatively, under the terms of the ordinary General Public License). To apply these terms, attach the following notices to the library. It is safest to attach them to the start of each source file to most effectively convey the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA Also add information on how to contact you by electronic and paper mail. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the library, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the library `Frob' (a library for tweaking knobs) written by James Random Hacker. , 1 April 1990 Ty Coon, President of Vice That's all there is to it! ocamlweb-1.41/ocamllex-parser/0000755000246300004300000000000013422556307015666 5ustar filliatrvalsocamlweb-1.41/ocamllex-parser/lex_syntax.mli0000644000246300004300000000267313422556307020577 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* The shallow abstract syntax *) type location = { start_pos: Lexing.position; end_pos: Lexing.position; start_line: int; start_col: int } type regular_expression = Epsilon | Characters of int list | Sequence of regular_expression * regular_expression | Alternative of regular_expression * regular_expression | Repetition of regular_expression | Ident of string * location type lexer_definition = { header: location; named_regexps : (string * location * regular_expression) list; entrypoints: (string * location * (regular_expression * location) list) list; trailer: location } ocamlweb-1.41/ocamllex-parser/lex_parser.mly0000644000246300004300000000723413422556307020563 0ustar filliatrvals/***********************************************************************/ /* */ /* Objective Caml */ /* */ /* Xavier Leroy, projet Cristal, INRIA Rocquencourt */ /* */ /* Copyright 1996 Institut National de Recherche en Informatique et */ /* en Automatique. All rights reserved. This file is distributed */ /* under the terms of the Q Public License version 1.0. */ /* */ /***********************************************************************/ /* $Id$ */ /* The grammar for lexer definitions */ %{ open Lex_syntax (* Auxiliaries for the parser. *) let named_regexps = (Hashtbl.create 13 : (string, regular_expression) Hashtbl.t) let regexp_for_string s = let rec re_string n = if n >= String.length s then Epsilon else if succ n = String.length s then Characters([Char.code (s.[n])]) else Sequence(Characters([Char.code (s.[n])]), re_string (succ n)) in re_string 0 let char_class c1 c2 = let rec cl n = if n > c2 then [] else n :: cl(succ n) in cl c1 let all_chars = char_class 0 255 let rec subtract l1 l2 = match l1 with [] -> [] | a::r -> if List.mem a l2 then subtract r l2 else a :: subtract r l2 %} %token Tident %token Tchar %token Tstring %token Taction %token Trule Tparse Tand Tequal Tend Tor Tunderscore Teof Tlbracket Trbracket %token Tstar Tmaybe Tplus Tlparen Trparen Tcaret Tdash Tlet %left Tor %left CONCAT %nonassoc Tmaybe %left Tstar %left Tplus %start lexer_definition %type lexer_definition %% lexer_definition: header named_regexps Trule definition other_definitions header Tend { {header = $1; named_regexps = List.rev $2; entrypoints = $4 :: List.rev $5; trailer = $6} } ; header: Taction { $1 } | /*epsilon*/ { { start_pos = Lexing.dummy_pos; end_pos = Lexing.dummy_pos; start_line = 1; start_col = 0 } } ; named_regexps: named_regexps Tlet Tident Tequal regexp { let (s,l) = $3 in (s,l,$5)::$1 } | /*epsilon*/ { [] } ; other_definitions: other_definitions Tand definition { $3::$1 } | /*epsilon*/ { [] } ; definition: Tident Tequal entry { let(s,l)=$1 in (s,l,$3) } ; entry: Tparse case rest_of_entry { $2::List.rev $3 } | Tparse rest_of_entry { List.rev $2 } ; rest_of_entry: rest_of_entry Tor case { $3::$1 } | { [] } ; case: regexp Taction { ($1,$2) } ; regexp: Tunderscore { Characters all_chars } | Teof { Characters [256] } | Tchar { Characters [$1] } | Tstring { regexp_for_string $1 } | Tlbracket char_class Trbracket { Characters $2 } | regexp Tstar { Repetition $1 } | regexp Tmaybe { Alternative($1, Epsilon) } | regexp Tplus { Sequence($1, Repetition $1) } | regexp Tor regexp { Alternative($1,$3) } | regexp regexp %prec CONCAT { Sequence($1,$2) } | Tlparen regexp Trparen { $2 } | Tident { let (s,l)=$1 in Ident(s,l) } ; char_class: Tcaret char_class1 { subtract all_chars $2 } | char_class1 { $1 } ; char_class1: Tchar Tdash Tchar { char_class $1 $3 } | Tchar { [$1] } | char_class1 char_class1 %prec CONCAT { $1 @ $2 } ; %% ocamlweb-1.41/ocamllex-parser/lex_lexer.mll0000644000246300004300000001373413422556307020373 0ustar filliatrvals(***********************************************************************) (* *) (* Objective Caml *) (* *) (* Xavier Leroy, projet Cristal, INRIA Rocquencourt *) (* *) (* Copyright 1996 Institut National de Recherche en Informatique et *) (* en Automatique. All rights reserved. This file is distributed *) (* under the terms of the Q Public License version 1.0. *) (* *) (***********************************************************************) (* $Id$ *) (* The lexical analyzer for lexer definitions. Bootstrapped! *) { open Lex_syntax open Lex_parser (* Auxiliaries for the lexical analyzer *) let brace_depth = ref 0 and comment_depth = ref 0 exception Lexical_error of string * int * int let string_buffer = Buffer.create 256 let reset_string_buffer () = Buffer.reset string_buffer let store_string_char c = Buffer.add_char string_buffer c let get_stored_string () = Buffer.contents string_buffer let char_for_backslash = function 'n' -> '\n' | 't' -> '\t' | 'b' -> '\b' | 'r' -> '\r' | c -> c let char_for_decimal_code lexbuf i = Char.chr(100 * (Char.code(Lexing.lexeme_char lexbuf i) - 48) + 10 * (Char.code(Lexing.lexeme_char lexbuf (i+1)) - 48) + (Char.code(Lexing.lexeme_char lexbuf (i+2)) - 48)) let line_num = ref 1 let line_start_pos = ref 0 let handle_lexical_error fn lexbuf = let line = !line_num and column = Lexing.lexeme_start lexbuf - !line_start_pos in try fn lexbuf with Lexical_error(msg, _, _) -> raise(Lexical_error(msg, line, column)) let cur_loc lexbuf = { start_pos = Lexing.lexeme_start_p lexbuf; end_pos = Lexing.lexeme_end_p lexbuf; start_line = !line_num; start_col = Lexing.lexeme_start lexbuf - !line_start_pos } } rule main = parse [' ' '\013' '\009' '\012' ] + { main lexbuf } | '\010' { line_start_pos := Lexing.lexeme_end lexbuf; incr line_num; main lexbuf } | "(*" { comment_depth := 1; handle_lexical_error comment lexbuf; main lexbuf } | ['A'-'Z' 'a'-'z'] ['A'-'Z' 'a'-'z' '\'' '_' '0'-'9'] * { match Lexing.lexeme lexbuf with "rule" -> Trule | "parse" -> Tparse | "and" -> Tand | "eof" -> Teof | "let" -> Tlet | s -> let l = cur_loc lexbuf in (*i Printf.eprintf "ident '%s' occurs at (%d,%d)\n" s l.start_pos l.end_pos; i*) Tident (s,l) } | '"' { reset_string_buffer(); handle_lexical_error string lexbuf; Tstring(get_stored_string()) } | "'" [^ '\\'] "'" { Tchar(Char.code(Lexing.lexeme_char lexbuf 1)) } | "'" '\\' ['\\' '\'' 'n' 't' 'b' 'r'] "'" { Tchar(Char.code(char_for_backslash (Lexing.lexeme_char lexbuf 2))) } | "'" '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { Tchar(Char.code(char_for_decimal_code lexbuf 2)) } | '{' { let n1 = Lexing.lexeme_end_p lexbuf and l1 = !line_num and s1 = !line_start_pos in brace_depth := 1; let n2 = handle_lexical_error action lexbuf in Taction({start_pos = n1; end_pos = n2; start_line = l1; start_col = n1.Lexing.pos_cnum - s1}) } | '=' { Tequal } | '|' { Tor } | '_' { Tunderscore } | '[' { Tlbracket } | ']' { Trbracket } | '*' { Tstar } | '?' { Tmaybe } | '+' { Tplus } | '(' { Tlparen } | ')' { Trparen } | '^' { Tcaret } | '-' { Tdash } | eof { Tend } | _ { raise(Lexical_error ("illegal character " ^ String.escaped(Lexing.lexeme lexbuf), !line_num, Lexing.lexeme_start lexbuf - !line_start_pos)) } and action = parse '{' { incr brace_depth; action lexbuf } | '}' { decr brace_depth; if !brace_depth = 0 then Lexing.lexeme_start_p lexbuf else action lexbuf } | '"' { reset_string_buffer(); string lexbuf; reset_string_buffer(); action lexbuf } | "'" [^ '\\'] "'" { action lexbuf } | "'" '\\' ['\\' '\'' 'n' 't' 'b' 'r'] "'" { action lexbuf } | "'" '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { action lexbuf } | "(*" { comment_depth := 1; comment lexbuf; action lexbuf } | eof { raise (Lexical_error("unterminated action", 0, 0)) } | '\010' { line_start_pos := Lexing.lexeme_end lexbuf; incr line_num; action lexbuf } | _ { action lexbuf } and string = parse '"' { () } | '\\' [' ' '\013' '\009' '\012'] * '\010' [' ' '\013' '\009' '\012'] * { line_start_pos := Lexing.lexeme_end lexbuf; incr line_num; string lexbuf } | '\\' ['\\' '"' 'n' 't' 'b' 'r'] { store_string_char(char_for_backslash(Lexing.lexeme_char lexbuf 1)); string lexbuf } | '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] { store_string_char(char_for_decimal_code lexbuf 1); string lexbuf } | eof { raise(Lexical_error("unterminated string", 0, 0)) } | '\010' { store_string_char '\010'; line_start_pos := Lexing.lexeme_end lexbuf; incr line_num; string lexbuf } | _ { store_string_char(Lexing.lexeme_char lexbuf 0); string lexbuf } and comment = parse "(*" { incr comment_depth; comment lexbuf } | "*)" { decr comment_depth; if !comment_depth = 0 then () else comment lexbuf } | '"' { reset_string_buffer(); string lexbuf; reset_string_buffer(); comment lexbuf } | "''" { comment lexbuf } | "'" [^ '\\' '\''] "'" { comment lexbuf } | "'\\" ['\\' '\'' 'n' 't' 'b' 'r'] "'" { comment lexbuf } | "'\\" ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { comment lexbuf } | eof { raise(Lexical_error("unterminated comment", 0, 0)) } | '\010' { line_start_pos := Lexing.lexeme_end lexbuf; incr line_num; comment lexbuf } | _ { comment lexbuf } ocamlweb-1.41/doc/0000755000246300004300000000000013422556306013334 5ustar filliatrvalsocamlweb-1.41/doc/ocamlweb-1.41-man.tex0000644000246300004300000005120213422556306017001 0ustar filliatrvals\documentclass[12pt]{article} \usepackage[T1]{fontenc} \usepackage[latin1]{inputenc} \usepackage{fullpage} \usepackage{url} \newcommand{\WEB}{\textsf{WEB}} \newcommand{\Caml}{\textsf{Caml}} \newcommand{\OCaml}{\textsf{Objective Caml}} \newcommand{\ocamlweb}{\textsf{ocamlweb}} \newcommand{\monurl}[1]{#1} %HEVEA\renewcommand{\monurl}[1]{\ahref{#1}{#1}} %HEVEA\newcommand{\lnot}{not} %HEVEA\newcommand{\lor}{or} %HEVEA\newcommand{\land}{\&} \begin{document} %%% titre %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \title{ocamlweb: a literate programming tool \\ for Objective Caml} \author{Jean-Christophe Filli\^{a}tre and Claude March\'e \\ \normalsize\monurl{\url{http://www.lri.fr/~filliatr/ocamlweb}}} \date{} \maketitle \tableofcontents %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{Introduction} Literate programming has been introduced by D.~E.~Knuth in 1984. The main idea is to put the code and its documentation in the same file and to produce from it a document which is readable by a human, and not only by a machine. Although \ocamlweb\ borrows a lot of ideas from Knuth's original tool (called \WEB), there are big differences between them. First, \WEB\ allows you to present the pieces of your code in any order, and this is quite useful when using poorly structured languages, like \textsf{Pascal} or \textsf{C}. But \OCaml\ is already highly structured, and this is no more useful. Moreover, \WEB\ requires the use of a tool to produce the code from the \WEB\ file, which greatly complicates the use of your favorite source-based tools (dependencies generator, debugger, emacs mode, etc.). When using \ocamlweb, the documentation is inserted in the code as comments (in the \Caml\ sense), and your code is not linked to the existence of \ocamlweb\ in any way. Currently, the task of \ocamlweb\ may be seen as: \begin{enumerate} \item making a nice document with the code and its documentation; \item generating a global index of cross-references, where each identifier is associated to the lists of sections where it is defined or used. \end{enumerate} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{Principles} Documentation is inserted into \Caml\ files as \emph{comments}. Thus your files may compile as usual, whether you use \ocamlweb\ or not. \ocamlweb\ presupposes that the given \Caml\ files are well-formed (at least lexically, but also syntactically if you want the cross references to be correct). \ocamlweb\ understands each \Caml\ file as a sequence of paragraphs, each paragraph being either a piece of code or a piece of documentation. Documentation starts and ends with \Caml\ comment's delimiters \texttt{(*} and \texttt{*)}, and is a regular \LaTeX\ text. Code starts with any characters sequence other than \texttt{(*} and ends with an empty line. Two styles are available for the final document: \begin{itemize} \item a \WEB\ style, where the code and documentation are displayed in \emph{sections}, numbered consecutively starting from~1. A new section is started at the beginning of each file. You can also start a new section manually (see the paragraph below about controls); \item a \LaTeX\ style, where you structure your document as you like, using the usual sectioning commands of \LaTeX. \end{itemize} \paragraph{Escapings: code inside documentation and vice versa.} The first feature you will require is the ability to quote code inside documentation and conversely. The latter, namely documentation inside code, is simply obtained by normal \Caml\ comments filled in with a \LaTeX\ contents. The former is obtained by quoting code between the delimiters \texttt{[} and \texttt{]}. Square brackets may be nested, the inner ones being understood as being part of the quoted code (thus you can quote a list expression like $[1;2;3]$ by writing \texttt{[[1;2;3]]}). Inside quotations, the code is pretty-printed in the same way as it is in code parts. \paragraph{Controls.} In addition to the default behavior of \ocamlweb, you can control it through a small set of commands, which are comments of a particular shape. These commands are the following: \begin{description} \item[\texttt{(*s}] ~\par Starts a new section. (Meaningless in \LaTeX\ style.) \item[\texttt{(*i} \quad\dots\quad \texttt{i*)}] ~\par Ignores all the text between those two delimiters. Such ``comments'' cannot be nested but any \Caml\ code and comments may appear between them, included nested \Caml\ comments. You can use those delimiters to enclose a comment that shouldn't appear in the document, but also to hide some \Caml\ code, putting it between \texttt{(*i*)} and \texttt{(*i*)} in such a way that your code still compiles but is ignored by \ocamlweb. (Notice that if you use the delimiters \texttt{(*i} and \texttt{i*)} directly, the text enclosed is commented for both \Caml\ and \ocamlweb.) \item[\texttt{(*c}] ~\par Tells \ocamlweb\ that this is a real \Caml\ comment an not a documentation text. Mainly useful is you want to insert comments after empty lines. However, this is not the spirit of \ocamlweb, and you are encouraged to put the documentation in separate \LaTeX\ paragraphs and not in traditional \Caml\ comments. \item[\texttt{(*r}] ~\par Justifies an end-of-line comment on the right margin. \item[\texttt{(*p} \quad\dots\quad \texttt{*)}] ~\par Insert some material in the \LaTeX\ preamble. See also command line option \verb!-p!. \end{description} \paragraph{Pretty-printing.} \ocamlweb\ uses different faces for identifiers and keywords, and use mathematical symbols for some \Caml\ tokens. Here are the correspondences. \begin{center} \begin{tabular}{ll@{\qquad\qquad}ll@{\qquad\qquad}ll@{\qquad\qquad}} \verb!->! & $\rightarrow$ & \verb!<-! & $\leftarrow$ & \verb|*| & $\times$ \\ \verb|<=| & $\le$ & \verb|>=| & $\ge$ & \verb|~-| & $-$ \\ \verb|<>| & $\not=$ & \verb|==| & $\equiv$ & \verb|!=| & $\not\equiv$ \\ \verb|or|, \verb!||! & $\lor$ & \verb|&|, \verb|&&| & $\land$ & \verb|not| & $\lnot$ \end{tabular} \end{center} Integers and floating-point literals are pretty-printed like this: \begin{center} \begin{tabular}{l@{$\quad\rightarrow\quad$}l} \verb|123| & $123$ \\ \verb|0b010011| & $010011_2$ \\ \verb|0o466| & $466_8$ \\ \verb|0x3fff| & $\mathtt{3fff}_{16}$ \\ \verb|1.2e6| & $1.2\cdot 10^6$ \\ \verb|1e-4| & $10^{-4}$ \end{tabular} \end{center} Characters strings are pretty-printed in fixed-width %HEVEAfont. %BEGIN LATEX font, and spaces are explicitly shown as the symbol {\tt\char`\ }, as in \texttt{"a\char`\ constant\char`\ string"}. %END LATEX %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{Hints to get a pretty document} \ocamlweb\ is rather robust, in the sense that it will always succeed in producing a document, as soon as the \Caml\ files are lexically correct. However, you may find the result rather ugly if so were your source files. Here are some style hints to get a pretty document. First, \ocamlweb\ is not a real code pretty-printer: it does not indent your code, and it does not even cut your code lines when they are too long. The code will always appear formatted as it is in the source files. The indentation at the beggining of each line is output as a proportional space (tabulations are correctly translated). In particular, if you want your pattern-matchings to be aligned, you have to put a `\verb!|!' also in front of the first pattern. Here is the difference: \begin{displaymath} \begin{array}{l} \mathsf{let}~\mathit{f}~=~\mathsf{function} \\ \hspace*{2em}\mathit{O}~\rightarrow~\dots \\ \hspace*{1em}|~(\mathit{S}~p)~\rightarrow~\dots \end{array} \qquad\qquad \begin{array}{l} \mathsf{let}~\mathit{f}~=~\mathsf{function} \\ \hspace*{1em}|~\mathit{O}~\rightarrow~\dots \\ \hspace*{1em}|~(\mathit{S}~p)~\rightarrow~\dots \end{array} \end{displaymath} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{Usage} \ocamlweb\ is invoked on a shell command line as follows: \begin{displaymath} \texttt{ocamlweb }<\textit{options and files}> \end{displaymath} Any command line argument which is not an option is considered to be a file (even if it starts with a \verb!-!). \Caml\ files are identified by the suffixes \verb!.ml! and \verb!.mli!, and \LaTeX\ files by the suffix \verb!.tex!. The latter will be copied `as is' in the final document. The order of files on the command line is kept in the final document. \subsection*{Command line options} %%% attention : -- dans un argument de \texttt est affiché comme un %%% seul - d'où l'utilisation de la macro suivante \newcommand{\mm}{\symbol{45}\symbol{45}} \begin{description} \item[\texttt{-o }\textit{file}, \texttt{\mm{}output }\textit{file}] ~\par Redirects the output into the file `\textit{file}'. \item[\texttt{\mm{}noweb}] ~\par In that case, there are no sections à la WEB, and the user structurates his document directly through \LaTeX\ commands, like for instance \verb|\section|, \verb|\subsection|, etc. There is still an index, in the usual \LaTeX\ sense. (Therefore, if you have introduced \LaTeX\ sections and subsections, their numbers will appear in the index.) \item[\texttt{-s }, \texttt{\mm{}short}] ~\par Do not insert titles for the files. The default behavior is to insert a title like ``Module Foo'' or ``Interface for module Foo'' for each file. \item[\texttt{\mm{}no-index}] ~\par Do not output the index. \item[\texttt{\mm{}dvi}] ~\par Output in DVI format, instead of \LaTeX\ format. (You need \texttt{latex} to be installed and present in your path.) \item[\texttt{\mm{}ps}] ~\par Output in PostScript format, instead of \LaTeX\ format. (You need both \texttt{latex} and \texttt{dvips} to be installed and present in your path.) \item[\texttt{\mm{}html}] ~\par Output in HTML format, instead of \LaTeX\ format. (You need both \texttt{latex} and \texttt{hevea} to be installed and present in your path.) \item[\texttt{\mm{}hevea-option }\textit{option}] ~\par Passes the given option to \texttt{hevea} (to be used with the \texttt{\mm{}html} option). It is mainly useful to specify where the file \texttt{ocamlweb.sty} is to be found, when not installed in the \texttt{hevea} library directory, using \texttt{\mm{}hevea-option "-I }\textit{dir}\texttt{"}. \item[\texttt{\mm{}extern-defs}] ~\par Keeps the external definitions in the index i.e. the identifiers which are not defined in any part of the code. (The default behavior is to suppress them from the index, even if they are used somewhere in the code.) \item[\texttt{\mm{}header}] ~\par Does not skip the header of \Caml\ files. The default behavior is to skip them, since there are usually made of copyright and license informations, which you do not want to see in the final document. Headers are identified as comments right at the beginning of the \Caml\ file, and are stopped by any character other then a space outside a comment or by an empty line. \item[\texttt{\mm{}no-preamble}] ~\par Suppresses the header and trailer of the final document. Thus, you can insert the resulting document into a larger one. \item[\texttt{-p} \textit{string}, \texttt{\mm{}preamble} \textit{string}]~\par Insert some material in the \LaTeX\ preamble, right before \verb!\begin{document}!. See also the control \texttt{(*p}. \item[\texttt{\mm{}class-options }\textit{options}] ~\par Sets the \LaTeX\ document class options; it defaults to \verb!12pt!. \item[\texttt{\mm{}latex-option }\textit{option}] ~\par Passes the given option the \LaTeX\ package \texttt{ocamlweb.sty}. \item[\texttt{\mm{}old-fullpage}] ~ \par Uses the old version of the \LaTeX\ \texttt{fullpage} package, i.e. with no option. Otherwise option \texttt{headings} is used. \item[\texttt{\mm{}impl }\textit{file}, \texttt{\mm{}intf }\textit{file}, \texttt{\mm{}tex }\textit{file}] ~\par Considers the file `\textit{file}' respectively as a \verb!.ml! file, a \verb!.mli! file or a \verb!.tex! file. \item[\texttt{\mm{}files }\textit{file}] ~\par Read file names to process in file `\textit{file}' as if they were given on the command line. Useful for program sources splitted in several directories. See FAQ. \item[\texttt{\mm{}no-greek}] ~\par Disable use of greek letters for single-letter type variables. For example, the declaration of \verb|List.hd| is displayed as \begin{quote} \textit{List.hd} : $\alpha$ \textit{list} $\rightarrow$ $\alpha$ \end{quote} but with this option, it will be displayed as \begin{quote} \textit{List.hd} : \textit{'a} \textit{list} $\rightarrow$ \textit{'a} \end{quote} \item[\texttt{-q}, \texttt{\mm{}quiet}] ~\par Be quiet. Do not print anything on standard error output except errors. \item[\texttt{-h}, \texttt{\mm{}help}] ~\par Gives a short summary of the options and exits. \item[\texttt{-v}, \texttt{\mm{}version}] ~\par Prints the version and exits. \end{description} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{The \texttt{ocamlweb} \LaTeX{} style file} \label{section:ocamlweb.sty} In case you choose to produce a document without the default \LaTeX{} preamble (by using option \verb|--no-preamble|), then you must insert into your own preamble the command \begin{quote} \verb|\usepackage[|\textit{options}\verb|]{ocamlweb}| \end{quote} Alternatively, you may also pass these options with the \verb|--latex-options| option of the \verb|ocamlweb| command. The options that you may pass to the package are the following: \begin{description} \item[\texttt{noweb}] ~ Tells \verb|ocamlweb.sty| that the document was generated with the \verb|--noweb| option so that no WEB sections are used, and the index was generated by referencing the \LaTeX\ sections, subsections, etc. \item[\texttt{novisiblespaces}] ~ By default, spaces in strings of CAML code parts are output as \texttt{\char`\ }. They will be output as real spaces if you select this option. \item[\texttt{bypages} / \texttt{bysections}] ~ When not in WEB sectioning style, these options specify whether the index must refer to page numbers or section numbers. \texttt{bypages} is the default. In WEB sectioning style, this option has no effect. \end{description} Additionally, you may alter the rendering of the document by redefining some macros: \begin{description} \item[\texttt{ocwkw}, \texttt{ocwbt}, \texttt{ocwupperid}, \texttt{ocwlowerid}, \texttt{ocwtv}] ~ The one-argument macros to typeset keywords, base types (such as \verb|int|, \verb|string|, etc.), uppercase identifiers (type constructors, exception names, module names), lowercase identifiers and type variables respectively. Defaults are sans-serif for keywords and italic for all others. Some of the single-letter type variables are displayed by default as greek letters, but this behaviour can be selected by the \verb|--no-greek| option. For example, if you would like a slanted font for base types, you may insert \begin{verbatim} \renewcommand{\ocwbt}[1]{\textsl{#1}} \end{verbatim} anywhere between \verb|\usepackage{ocamlweb}| and \verb|\begin{document}|. \item[\texttt{ocwlexkw}, \texttt{ocwlexident}, \texttt{ocwyacckw}, \texttt{ocwyaccident}] ~ Analogous macros as above, to typeset lex keywords, lex identifiers, yacc keywords and yacc identifiers respectively. \item[\texttt{ocwinterface}, \texttt{ocwmodule}, \texttt{ocwinterfacepart}, \texttt{ocwcodepart}] ~ One-argument macros for typesetting the title of a \verb|.mli| file, the title of a \verb|.ml| file, the interface part of a \verb|.ml| file and the code part of a \verb|.ml| file, respectively. Defaults are is \begin{verbatim} \newcommand{\ocwinterface}[1]{\section*{Interface for module #1}} \newcommand{\ocwmodule}[1]{\section*{Module #1}} \newcommand{\ocwinterfacepart}{\subsection*{Interface}} \newcommand{\ocwcodepart}{\subsection*{Code}} \end{verbatim} and you may redefine them using \verb|\renewcommand|. \end{description} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \section{FAQ} \begin{enumerate} \item \textbf{What about an HTML output?} ~\par Use \textsf{hevea}, the \LaTeX\ to HTML translator written by Luc Maranget (freely available at \monurl{\url{http://pauillac.inria.fr/hevea/}}), with the following command-line: \begin{displaymath} \texttt{hevea} ~ \texttt{ocamlweb.sty} ~ \textit{file.tex} \end{displaymath} where \textit{file.tex} is the document produced by \ocamlweb. The package \texttt{ocamlweb.sty} contains the necessary support for \textsf{hevea}. \item \textbf{How can I customize the appearance of the final document?} ~\par %Make your own version of the \LaTeX\ package %\texttt{ocamlweb.sty}. There are macros for keywords, identifiers, %index entries, etc. with short comments explaining their role. % jcf, tu nous fais le coup a chaque fois: tu sais bien que ce n'est % pas la bonne manière de faire car l'utilisateur ne peut plus se % mettre a jour ! You can redefine some of the \LaTeX{} macros of the \verb|ocamlweb.sty| style file. See Section~\ref{section:ocamlweb.sty}. We do not recommend to modify the \verb|ocamlweb.sty| file directly, since you would not be able to update easily to future versions. You should rather redefine the macros using \verb|\renewcommand|. If you want to customize other parameters that are not currently customizable, please contact the developers. \item \textbf{How can I insert `usepackage' commands, or whatever else, in the \LaTeX\ preamble?} ~\par Use the option \texttt{-p} or the corresponding control \texttt{(*p}. If you really want a different \LaTeX\ preamble, for instance to use a \LaTeX\ class other than \texttt{article}, then use the option \texttt{\mm{}no-preamble} and catenate the result with your own header and trailer (or use a \verb|\input| or \verb|\include| command to insert the file generated by \ocamlweb\ in your main \LaTeX\ file.) \item \textbf{How can I use square brackets in \LaTeX, since they are reserved characters for \ocamlweb?} ~\par There is no escape sequence for the moment. But there is an easy solution to this problem: define macros for your \LaTeX\ notations involving square brackets and put them in the preamble or in a \verb|.tex| file that you will provide on the \ocamlweb\ command line. Then, there is no longer square brackets in your source comments, but only calls to these macros. \item \textbf{What about lexers and parsers?} ~\par There is support for \textsf{ocamllex} lexers and \textsf{ocamlyacc} parsers since version 0.9. They are recognized by their suffix on the command line (do not use option \verb!--impl! anymore). \item \textbf{I would like my pattern-matching right-hand sides to be aligned. Is it possible?} ~\par No, it is not, since \ocamlweb\ uses proportional fonts. But you can still align your pattern-matching in your source files, since \ocamlweb\ converts multiple spaces into single ones. \item \textbf{What can I do with a large program with sources in several directories, organised as libraries?} ~ First alternative: you can run an ocamlweb command in each directories, producing a documentation for each library. If you want to have the documentations alltogether in the same TeX file, run each ocamlweb commands with option \texttt{\mm{}no-preamble} to avoid generation of the \LaTeX\ preamble, build by hand a master document file with the preamble you want, without forgetting the \verb|\usepackage{ocamlweb}|, and input each file in each directory with the \verb|\input| or the \verb|\include| macro. Second alternative: the main problem with the first alternative is that you will have an separate index for each libraries. If you want a global index, you need the run only one \verb|ocamlweb| command. If you don't want to put all source file names on one single command line, you can use the \verb|--files| option which allows you to read the source file names from a file. Example : \begin{verbatim} ocamlweb --files lib1/source-files --files lib2/source-files \end{verbatim} will produce documentation for files in \verb|lib1| and \verb|lib2| provided that the files \verb|source-files| in each directory contain the name of the documented source files. \end{enumerate} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \end{document} %%% Local Variables: %%% mode: latex %%% TeX-master: t %%% End: ocamlweb-1.41/doc/ocamlweb-1.41-man.html0000644000246300004300000011637213422556306017157 0ustar filliatrvals ocamlweb-1.41-man

ocamlweb: a literate programming tool
for Objective Caml

Jean-Christophe Filliâtre and Claude Marché
http://www.lri.fr/~filliatr/ocamlweb

Contents

1  Introduction

Literate programming has been introduced by D. E. Knuth in 1984. The main idea is to put the code and its documentation in the same file and to produce from it a document which is readable by a human, and not only by a machine. Although ocamlweb borrows a lot of ideas from Knuth’s original tool (called WEB), there are big differences between them. First, WEB allows you to present the pieces of your code in any order, and this is quite useful when using poorly structured languages, like Pascal or C. But Objective Caml is already highly structured, and this is no more useful. Moreover, WEB requires the use of a tool to produce the code from the WEB file, which greatly complicates the use of your favorite source-based tools (dependencies generator, debugger, emacs mode, etc.). When using ocamlweb, the documentation is inserted in the code as comments (in the Caml sense), and your code is not linked to the existence of ocamlweb in any way.

Currently, the task of ocamlweb may be seen as:

  1. making a nice document with the code and its documentation;
  2. generating a global index of cross-references, where each identifier is associated to the lists of sections where it is defined or used.

2  Principles

Documentation is inserted into Caml files as comments. Thus your files may compile as usual, whether you use ocamlweb or not. ocamlweb presupposes that the given Caml files are well-formed (at least lexically, but also syntactically if you want the cross references to be correct). ocamlweb understands each Caml file as a sequence of paragraphs, each paragraph being either a piece of code or a piece of documentation. Documentation starts and ends with Caml comment’s delimiters (* and *), and is a regular LATEX text. Code starts with any characters sequence other than (* and ends with an empty line.

Two styles are available for the final document:

  • a WEB style, where the code and documentation are displayed in sections, numbered consecutively starting from 1. A new section is started at the beginning of each file. You can also start a new section manually (see the paragraph below about controls);
  • a LATEX style, where you structure your document as you like, using the usual sectioning commands of LATEX.

Escapings: code inside documentation and vice versa.

The first feature you will require is the ability to quote code inside documentation and conversely. The latter, namely documentation inside code, is simply obtained by normal Caml comments filled in with a LATEX contents. The former is obtained by quoting code between the delimiters [ and ]. Square brackets may be nested, the inner ones being understood as being part of the quoted code (thus you can quote a list expression like [1;2;3] by writing [[1;2;3]]). Inside quotations, the code is pretty-printed in the same way as it is in code parts.

Controls.

In addition to the default behavior of ocamlweb, you can control it through a small set of commands, which are comments of a particular shape. These commands are the following:

(*s
 

Starts a new section. (Meaningless in LATEX style.)

(*i   …  i*)
 

Ignores all the text between those two delimiters. Such “comments” cannot be nested but any Caml code and comments may appear between them, included nested Caml comments. You can use those delimiters to enclose a comment that shouldn’t appear in the document, but also to hide some Caml code, putting it between (*i*) and (*i*) in such a way that your code still compiles but is ignored by ocamlweb. (Notice that if you use the delimiters (*i and i*) directly, the text enclosed is commented for both Caml and ocamlweb.)

(*c
 

Tells ocamlweb that this is a real Caml comment an not a documentation text. Mainly useful is you want to insert comments after empty lines. However, this is not the spirit of ocamlweb, and you are encouraged to put the documentation in separate LATEX paragraphs and not in traditional Caml comments.

(*r
 

Justifies an end-of-line comment on the right margin.

(*p   …  *)
 

Insert some material in the LATEX preamble. See also command line option -p.

Pretty-printing.

ocamlweb uses different faces for identifiers and keywords, and use mathematical symbols for some Caml tokens. Here are the correspondences.

->         <-         *×         
<=         >=         ~-        
<>         ==         !=        
or, ||         &, &&         not¬         

Integers and floating-point literals are pretty-printed like this:

123  →  123
0b010011  →  0100112
0o466  →  4668
0x3fff  →  3fff16
1.2e6  →  1.2· 106
1e-4  →  10−4

Characters strings are pretty-printed in fixed-width font.

3  Hints to get a pretty document

ocamlweb is rather robust, in the sense that it will always succeed in producing a document, as soon as the Caml files are lexically correct. However, you may find the result rather ugly if so were your source files. Here are some style hints to get a pretty document.

First, ocamlweb is not a real code pretty-printer: it does not indent your code, and it does not even cut your code lines when they are too long. The code will always appear formatted as it is in the source files. The indentation at the beggining of each line is output as a proportional space (tabulations are correctly translated). In particular, if you want your pattern-matchings to be aligned, you have to put a ‘|’ also in front of the first pattern. Here is the difference:

  
    let f = function 
      O → … 
     | (S p) → …
        
    let f = function 
     | O → … 
     | (S p) → …

4  Usage

ocamlweb is invoked on a shell command line as follows:

  ocamlweb <options and files>

Any command line argument which is not an option is considered to be a file (even if it starts with a -). Caml files are identified by the suffixes .ml and .mli, and LATEX files by the suffix .tex. The latter will be copied ‘as is’ in the final document. The order of files on the command line is kept in the final document.

Command line options

-o file, --output file
 

Redirects the output into the file ‘file’.

--noweb
 

In that case, there are no sections à la WEB, and the user structurates his document directly through LATEX commands, like for instance \section, \subsection, etc. There is still an index, in the usual LATEX sense. (Therefore, if you have introduced LATEX sections and subsections, their numbers will appear in the index.)

-s , --short
 

Do not insert titles for the files. The default behavior is to insert a title like “Module Foo” or “Interface for module Foo” for each file.

--no-index
 

Do not output the index.

--dvi
 

Output in DVI format, instead of LATEX format. (You need latex to be installed and present in your path.)

--ps
 

Output in PostScript format, instead of LATEX format. (You need both latex and dvips to be installed and present in your path.)

--html
 

Output in HTML format, instead of LATEX format. (You need both latex and hevea to be installed and present in your path.)

--hevea-option option
 

Passes the given option to hevea (to be used with the --html option). It is mainly useful to specify where the file ocamlweb.sty is to be found, when not installed in the hevea library directory, using --hevea-option "-I dir".

--extern-defs
 

Keeps the external definitions in the index i.e. the identifiers which are not defined in any part of the code. (The default behavior is to suppress them from the index, even if they are used somewhere in the code.)

--header
 

Does not skip the header of Caml files. The default behavior is to skip them, since there are usually made of copyright and license informations, which you do not want to see in the final document. Headers are identified as comments right at the beginning of the Caml file, and are stopped by any character other then a space outside a comment or by an empty line.

--no-preamble
 

Suppresses the header and trailer of the final document. Thus, you can insert the resulting document into a larger one.

-p string, --preamble string
 

Insert some material in the LATEX preamble, right before \begin{document}. See also the control (*p.

--class-options options
 

Sets the LATEX document class options; it defaults to 12pt.

--latex-option option
 

Passes the given option the LATEX package ocamlweb.sty.

--old-fullpage
 

Uses the old version of the LATEX fullpage package, i.e. with no option. Otherwise option headings is used.

--impl file, --intf file, --tex file
 

Considers the file ‘file’ respectively as a .ml file, a .mli file or a .tex file.

--files file
 

Read file names to process in file ‘file’ as if they were given on the command line. Useful for program sources splitted in several directories. See FAQ.

--no-greek
 

Disable use of greek letters for single-letter type variables. For example, the declaration of List.hd is displayed as

List.hd : α list → α

but with this option, it will be displayed as

List.hd : ’a list’a
-q, --quiet
 

Be quiet. Do not print anything on standard error output except errors.

-h, --help
 

Gives a short summary of the options and exits.

-v, --version
 

Prints the version and exits.

5  The ocamlweb LATEX style file

In case you choose to produce a document without the default LATEX preamble (by using option --no-preamble), then you must insert into your own preamble the command

\usepackage[options]{ocamlweb}

Alternatively, you may also pass these options with the --latex-options option of the ocamlweb command.

The options that you may pass to the package are the following:

noweb
 

Tells ocamlweb.sty that the document was generated with the --noweb option so that no WEB sections are used, and the index was generated by referencing the LATEX sections, subsections, etc.

novisiblespaces
 

By default, spaces in strings of CAML code parts are output as . They will be output as real spaces if you select this option.

bypages / bysections
 

When not in WEB sectioning style, these options specify whether the index must refer to page numbers or section numbers. bypages is the default. In WEB sectioning style, this option has no effect.

Additionally, you may alter the rendering of the document by redefining some macros:

ocwkw, ocwbt, ocwupperid, ocwlowerid, ocwtv
 

The one-argument macros to typeset keywords, base types (such as int, string, etc.), uppercase identifiers (type constructors, exception names, module names), lowercase identifiers and type variables respectively. Defaults are sans-serif for keywords and italic for all others. Some of the single-letter type variables are displayed by default as greek letters, but this behaviour can be selected by the --no-greek option.

For example, if you would like a slanted font for base types, you may insert

     \renewcommand{\ocwbt}[1]{\textsl{#1}}

anywhere between \usepackage{ocamlweb} and \begin{document}.

ocwlexkw, ocwlexident, ocwyacckw, ocwyaccident
 

Analogous macros as above, to typeset lex keywords, lex identifiers, yacc keywords and yacc identifiers respectively.

ocwinterface, ocwmodule, ocwinterfacepart, ocwcodepart
 

One-argument macros for typesetting the title of a .mli file, the title of a .ml file, the interface part of a .ml file and the code part of a .ml file, respectively. Defaults are is

\newcommand{\ocwinterface}[1]{\section*{Interface for module #1}}
\newcommand{\ocwmodule}[1]{\section*{Module #1}}
\newcommand{\ocwinterfacepart}{\subsection*{Interface}}
\newcommand{\ocwcodepart}{\subsection*{Code}}

and you may redefine them using \renewcommand.

6  FAQ

  1. What about an HTML output?  

    Use hevea, the LATEX to HTML translator written by Luc Maranget (freely available at http://pauillac.inria.fr/hevea/), with the following command-line:

        hevea   ocamlweb.sty   file.tex

    where file.tex is the document produced by ocamlweb. The package ocamlweb.sty contains the necessary support for hevea.

  2. How can I customize the appearance of the final document?  

    You can redefine some of the LATEX macros of the ocamlweb.sty style file. See Section 5. We do not recommend to modify the ocamlweb.sty file directly, since you would not be able to update easily to future versions. You should rather redefine the macros using \renewcommand. If you want to customize other parameters that are not currently customizable, please contact the developers.

  3. How can I insert ‘usepackage’ commands, or whatever else, in the LATEX preamble?  

    Use the option -p or the corresponding control (*p.

    If you really want a different LATEX preamble, for instance to use a LATEX class other than article, then use the option --no-preamble and catenate the result with your own header and trailer (or use a \input or \include command to insert the file generated by ocamlweb in your main LATEX file.)

  4. How can I use square brackets in LATEX, since they are reserved characters for ocamlweb?  

    There is no escape sequence for the moment. But there is an easy solution to this problem: define macros for your LATEX notations involving square brackets and put them in the preamble or in a .tex file that you will provide on the ocamlweb command line. Then, there is no longer square brackets in your source comments, but only calls to these macros.

  5. What about lexers and parsers?  

    There is support for ocamllex lexers and ocamlyacc parsers since version 0.9. They are recognized by their suffix on the command line (do not use option --impl anymore).

  6. I would like my pattern-matching right-hand sides to be aligned. Is it possible?  

    No, it is not, since ocamlweb uses proportional fonts. But you can still align your pattern-matching in your source files, since ocamlweb converts multiple spaces into single ones.

  7. What can I do with a large program with sources in several directories, organised as libraries?  

    First alternative: you can run an ocamlweb command in each directories, producing a documentation for each library. If you want to have the documentations alltogether in the same TeX file, run each ocamlweb commands with option --no-preamble to avoid generation of the LATEX preamble, build by hand a master document file with the preamble you want, without forgetting the \usepackage{ocamlweb}, and input each file in each directory with the \input or the \include macro.

    Second alternative: the main problem with the first alternative is that you will have an separate index for each libraries. If you want a global index, you need the run only one ocamlweb command. If you don’t want to put all source file names on one single command line, you can use the --files option which allows you to read the source file names from a file. Example :

        ocamlweb --files lib1/source-files --files lib2/source-files
    

    will produce documentation for files in lib1 and lib2 provided that the files source-files in each directory contain the name of the documented source files.


This document was translated from LATEX by HEVEA.
ocamlweb-1.41/doc/ocamlweb.10000644000246300004300000000155113422556306015211 0ustar filliatrvals.TH ocamlweb 1 "June 15, 2001" .SH NAME ocamlweb \- A literate programming tool for Objective Caml .SH SYNOPSIS .B ocamlweb [ .B options ] .B files .SH DESCRIPTION .B ocamlweb is a literate programming tool for Objective Caml. It creates a LaTeX document with both documentation and code (implementations and interfaces) from a set of Caml files. Documentation is inserted into ocaml files as comments. Conversely, code may be quoted inside documentation between square brackets. See the ocamlweb web site for documentation and examples. .SH OPTIONS .TP .B \-h Help. Will give you the complete list of options accepted by ocamlweb. .SH AUTHORS .I Jean-Christophe Filliatre .br .I Claude Marche .SH SEE ALSO .I Ocamlweb web site: http://www.lri.fr/~filliatr/ocamlweb/ .br .I The Objective Caml web site: http://caml.inria.fr/ ocamlweb-1.41/support/0000755000246300004300000000000013422556307014304 5ustar filliatrvalsocamlweb-1.41/support/config.guess0000755000246300004300000006315713422556307016640 0ustar filliatrvals#! /bin/sh # Attempt to guess a canonical system name. # Copyright (C) 1992, 93, 94, 95, 96, 97, 1998 Free Software Foundation, Inc. # # This file is free software; you can redistribute it and/or modify it # under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, but # WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. # # As a special exception to the GNU General Public License, if you # distribute this file as part of a program that contains a # configuration script generated by Autoconf, you may include it under # the same distribution terms that you use for the rest of that program. # Written by Per Bothner . # The master version of this file is at the FSF in /home/gd/gnu/lib. # # This script attempts to guess a canonical system name similar to # config.sub. If it succeeds, it prints the system name on stdout, and # exits with 0. Otherwise, it exits with 1. # # The plan is that this can be called by configure scripts if you # don't specify an explicit system type (host/target name). # # Only a few systems have been added to this list; please add others # (but try to keep the structure clean). # # This is needed to find uname on a Pyramid OSx when run in the BSD universe. # (ghazi@noc.rutgers.edu 8/24/94.) if (test -f /.attbin/uname) >/dev/null 2>&1 ; then PATH=$PATH:/.attbin ; export PATH fi UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown trap 'rm -f dummy.c dummy.o dummy; exit 1' 1 2 15 # Note: order is significant - the case branches are not exclusive. case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in alpha:OSF1:*:*) if test $UNAME_RELEASE = "V4.0"; then UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'` fi # A Vn.n version is a released version. # A Tn.n version is a released field test version. # A Xn.n version is an unreleased experimental baselevel. # 1.2 uses "1.2" for uname -r. cat <dummy.s .globl main .ent main main: .frame \$30,0,\$26,0 .prologue 0 .long 0x47e03d80 # implver $0 lda \$2,259 .long 0x47e20c21 # amask $2,$1 srl \$1,8,\$2 sll \$2,2,\$2 sll \$0,3,\$0 addl \$1,\$0,\$0 addl \$2,\$0,\$0 ret \$31,(\$26),1 .end main EOF ${CC-cc} dummy.s -o dummy 2>/dev/null if test "$?" = 0 ; then ./dummy case "$?" in 7) UNAME_MACHINE="alpha" ;; 15) UNAME_MACHINE="alphaev5" ;; 14) UNAME_MACHINE="alphaev56" ;; 10) UNAME_MACHINE="alphapca56" ;; 16) UNAME_MACHINE="alphaev6" ;; esac fi rm -f dummy.s dummy echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[VTX]//' | tr [[A-Z]] [[a-z]]` exit 0 ;; 21064:Windows_NT:50:3) echo alpha-dec-winnt3.5 exit 0 ;; Amiga*:UNIX_System_V:4.0:*) echo m68k-cbm-sysv4 exit 0;; amiga:NetBSD:*:*) echo m68k-cbm-netbsd${UNAME_RELEASE} exit 0 ;; amiga:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; *:[Aa]miga[Oo][Ss]:*:*) echo ${UNAME_MACHINE}-unknown-amigaos exit 0 ;; arc64:OpenBSD:*:*) echo mips64el-unknown-openbsd${UNAME_RELEASE} exit 0 ;; arc:OpenBSD:*:*) echo mipsel-unknown-openbsd${UNAME_RELEASE} exit 0 ;; hkmips:OpenBSD:*:*) echo mips-unknown-openbsd${UNAME_RELEASE} exit 0 ;; pmax:OpenBSD:*:*) echo mipsel-unknown-openbsd${UNAME_RELEASE} exit 0 ;; sgi:OpenBSD:*:*) echo mips-unknown-openbsd${UNAME_RELEASE} exit 0 ;; wgrisc:OpenBSD:*:*) echo mipsel-unknown-openbsd${UNAME_RELEASE} exit 0 ;; arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) echo arm-acorn-riscix${UNAME_RELEASE} exit 0;; arm32:NetBSD:*:*) echo arm-unknown-netbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` exit 0 ;; SR2?01:HI-UX/MPP:*:*) echo hppa1.1-hitachi-hiuxmpp exit 0;; Pyramid*:OSx*:*:*|MIS*:OSx*:*:*) # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE. if test "`(/bin/universe) 2>/dev/null`" = att ; then echo pyramid-pyramid-sysv3 else echo pyramid-pyramid-bsd fi exit 0 ;; NILE:*:*:dcosx) echo pyramid-pyramid-svr4 exit 0 ;; sun4H:SunOS:5.*:*) echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` exit 0 ;; sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*) echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` exit 0 ;; i86pc:SunOS:5.*:*) echo i386-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` exit 0 ;; sun4*:SunOS:6*:*) # According to config.sub, this is the proper way to canonicalize # SunOS6. Hard to guess exactly what SunOS6 will be like, but # it's likely to be more like Solaris than SunOS4. echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` exit 0 ;; sun4*:SunOS:*:*) case "`/usr/bin/arch -k`" in Series*|S4*) UNAME_RELEASE=`uname -v` ;; esac # Japanese Language versions have a version number like `4.1.3-JL'. echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'` exit 0 ;; sun3*:SunOS:*:*) echo m68k-sun-sunos${UNAME_RELEASE} exit 0 ;; sun*:*:4.2BSD:*) UNAME_RELEASE=`(head -1 /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null` test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3 case "`/bin/arch`" in sun3) echo m68k-sun-sunos${UNAME_RELEASE} ;; sun4) echo sparc-sun-sunos${UNAME_RELEASE} ;; esac exit 0 ;; aushp:SunOS:*:*) echo sparc-auspex-sunos${UNAME_RELEASE} exit 0 ;; atari*:NetBSD:*:*) echo m68k-atari-netbsd${UNAME_RELEASE} exit 0 ;; atari*:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; sun3*:NetBSD:*:*) echo m68k-sun-netbsd${UNAME_RELEASE} exit 0 ;; sun3*:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; mac68k:NetBSD:*:*) echo m68k-apple-netbsd${UNAME_RELEASE} exit 0 ;; mac68k:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; mvme68k:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; mvme88k:OpenBSD:*:*) echo m88k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; powerpc:machten:*:*) echo powerpc-apple-machten${UNAME_RELEASE} exit 0 ;; macppc:NetBSD:*:*) echo powerpc-apple-netbsd${UNAME_RELEASE} exit 0 ;; RISC*:Mach:*:*) echo mips-dec-mach_bsd4.3 exit 0 ;; RISC*:ULTRIX:*:*) echo mips-dec-ultrix${UNAME_RELEASE} exit 0 ;; VAX*:ULTRIX*:*:*) echo vax-dec-ultrix${UNAME_RELEASE} exit 0 ;; 2020:CLIX:*:*) echo clipper-intergraph-clix${UNAME_RELEASE} exit 0 ;; mips:*:*:UMIPS | mips:*:*:RISCos) sed 's/^ //' << EOF >dummy.c int main (argc, argv) int argc; char **argv; { #if defined (host_mips) && defined (MIPSEB) #if defined (SYSTYPE_SYSV) printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0); #endif #if defined (SYSTYPE_SVR4) printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0); #endif #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD) printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0); #endif #endif exit (-1); } EOF ${CC-cc} dummy.c -o dummy \ && ./dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \ && rm dummy.c dummy && exit 0 rm -f dummy.c dummy echo mips-mips-riscos${UNAME_RELEASE} exit 0 ;; Night_Hawk:Power_UNIX:*:*) echo powerpc-harris-powerunix exit 0 ;; m88k:CX/UX:7*:*) echo m88k-harris-cxux7 exit 0 ;; m88k:*:4*:R4*) echo m88k-motorola-sysv4 exit 0 ;; m88k:*:3*:R3*) echo m88k-motorola-sysv3 exit 0 ;; AViiON:dgux:*:*) # DG/UX returns AViiON for all architectures UNAME_PROCESSOR=`/usr/bin/uname -p` if [ $UNAME_PROCESSOR = mc88100 -o $UNAME_PROCESSOR = mc88110 ] ; then if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx \ -o ${TARGET_BINARY_INTERFACE}x = x ] ; then echo m88k-dg-dgux${UNAME_RELEASE} else echo m88k-dg-dguxbcs${UNAME_RELEASE} fi else echo i586-dg-dgux${UNAME_RELEASE} fi exit 0 ;; M88*:DolphinOS:*:*) # DolphinOS (SVR3) echo m88k-dolphin-sysv3 exit 0 ;; M88*:*:R3*:*) # Delta 88k system running SVR3 echo m88k-motorola-sysv3 exit 0 ;; XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3) echo m88k-tektronix-sysv3 exit 0 ;; Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD) echo m68k-tektronix-bsd exit 0 ;; *:IRIX*:*:*) echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'` exit 0 ;; ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX. echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id exit 0 ;; # Note that: echo "'`uname -s`'" gives 'AIX ' i?86:AIX:*:*) echo i386-ibm-aix exit 0 ;; *:AIX:2:3) if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then sed 's/^ //' << EOF >dummy.c #include main() { if (!__power_pc()) exit(1); puts("powerpc-ibm-aix3.2.5"); exit(0); } EOF ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 rm -f dummy.c dummy echo rs6000-ibm-aix3.2.5 elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then echo rs6000-ibm-aix3.2.4 else echo rs6000-ibm-aix3.2 fi exit 0 ;; *:AIX:*:4) if /usr/sbin/lsattr -EHl proc0 | grep POWER >/dev/null 2>&1; then IBM_ARCH=rs6000 else IBM_ARCH=powerpc fi if [ -x /usr/bin/oslevel ] ; then IBM_REV=`/usr/bin/oslevel` else IBM_REV=4.${UNAME_RELEASE} fi echo ${IBM_ARCH}-ibm-aix${IBM_REV} exit 0 ;; *:AIX:*:*) echo rs6000-ibm-aix exit 0 ;; ibmrt:4.4BSD:*|romp-ibm:BSD:*) echo romp-ibm-bsd4.4 exit 0 ;; ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC NetBSD and echo romp-ibm-bsd${UNAME_RELEASE} # 4.3 with uname added to exit 0 ;; # report: romp-ibm BSD 4.3 *:BOSX:*:*) echo rs6000-bull-bosx exit 0 ;; DPX/2?00:B.O.S.:*:*) echo m68k-bull-sysv3 exit 0 ;; 9000/[34]??:4.3bsd:1.*:*) echo m68k-hp-bsd exit 0 ;; hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*) echo m68k-hp-bsd4.4 exit 0 ;; 9000/[3478]??:HP-UX:*:*) case "${UNAME_MACHINE}" in 9000/31? ) HP_ARCH=m68000 ;; 9000/[34]?? ) HP_ARCH=m68k ;; 9000/7?? | 9000/8?[1679] ) sed 's/^ //' << EOF >dummy.c #include #include int main () { #if defined(_SC_KERNEL_BITS) long bits = sysconf(_SC_KERNEL_BITS); #endif long cpu = sysconf (_SC_CPU_VERSION); switch (cpu) { case CPU_PA_RISC1_0: puts ("hppa1.0"); break; case CPU_PA_RISC1_1: puts ("hppa1.1"); break; case CPU_PA_RISC2_0: #if defined(_SC_KERNEL_BITS) switch (bits) { case 64: puts ("hppa2.0w"); break; case 32: puts ("hppa2.0n"); break; default: puts ("hppa2.0"); break; } break; #else /* !defined(_SC_KERNEL_BITS) */ puts ("hppa2.0"); break; #endif default: puts ("hppa1.0"); break; } exit (0); } EOF ${CC-cc} dummy.c -o dummy && HP_ARCH=`./dummy` rm -f dummy.c dummy esac HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'` echo ${HP_ARCH}-hp-hpux${HPUX_REV} exit 0 ;; 3050*:HI-UX:*:*) sed 's/^ //' << EOF >dummy.c #include int main () { long cpu = sysconf (_SC_CPU_VERSION); /* The order matters, because CPU_IS_HP_MC68K erroneously returns true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct results, however. */ if (CPU_IS_PA_RISC (cpu)) { switch (cpu) { case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break; case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break; case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break; default: puts ("hppa-hitachi-hiuxwe2"); break; } } else if (CPU_IS_HP_MC68K (cpu)) puts ("m68k-hitachi-hiuxwe2"); else puts ("unknown-hitachi-hiuxwe2"); exit (0); } EOF ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 rm -f dummy.c dummy echo unknown-hitachi-hiuxwe2 exit 0 ;; 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* ) echo hppa1.1-hp-bsd exit 0 ;; 9000/8??:4.3bsd:*:*) echo hppa1.0-hp-bsd exit 0 ;; hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* ) echo hppa1.1-hp-osf exit 0 ;; hp8??:OSF1:*:*) echo hppa1.0-hp-osf exit 0 ;; i?86:OSF1:*:*) if [ -x /usr/sbin/sysversion ] ; then echo ${UNAME_MACHINE}-unknown-osf1mk else echo ${UNAME_MACHINE}-unknown-osf1 fi exit 0 ;; parisc*:Lites*:*:*) echo hppa1.1-hp-lites exit 0 ;; C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) echo c1-convex-bsd exit 0 ;; C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) if getsysinfo -f scalar_acc then echo c32-convex-bsd else echo c2-convex-bsd fi exit 0 ;; C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) echo c34-convex-bsd exit 0 ;; C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) echo c38-convex-bsd exit 0 ;; C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) echo c4-convex-bsd exit 0 ;; CRAY*X-MP:*:*:*) echo xmp-cray-unicos exit 0 ;; CRAY*Y-MP:*:*:*) echo ymp-cray-unicos${UNAME_RELEASE} exit 0 ;; CRAY*[A-Z]90:*:*:*) echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \ | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \ -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ exit 0 ;; CRAY*TS:*:*:*) echo t90-cray-unicos${UNAME_RELEASE} exit 0 ;; CRAY-2:*:*:*) echo cray2-cray-unicos exit 0 ;; F300:UNIX_System_V:*:*) FUJITSU_SYS=`uname -p | tr [A-Z] [a-z] | sed -e 's/\///'` FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` echo "f300-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" exit 0 ;; F301:UNIX_System_V:*:*) echo f301-fujitsu-uxpv`echo $UNAME_RELEASE | sed 's/ .*//'` exit 0 ;; hp3[0-9][05]:NetBSD:*:*) echo m68k-hp-netbsd${UNAME_RELEASE} exit 0 ;; hp300:OpenBSD:*:*) echo m68k-unknown-openbsd${UNAME_RELEASE} exit 0 ;; i?86:BSD/386:*:* | *:BSD/OS:*:*) echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE} exit 0 ;; *:FreeBSD:*:*) echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` exit 0 ;; *:NetBSD:*:*) echo ${UNAME_MACHINE}-unknown-netbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` exit 0 ;; *:OpenBSD:*:*) echo ${UNAME_MACHINE}-unknown-openbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` exit 0 ;; i*:CYGWIN*:*) echo ${UNAME_MACHINE}-pc-cygwin32 exit 0 ;; i*:MINGW*:*) echo ${UNAME_MACHINE}-pc-mingw32 exit 0 ;; p*:CYGWIN*:*) echo powerpcle-unknown-cygwin32 exit 0 ;; prep*:SunOS:5.*:*) echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` exit 0 ;; *:GNU:*:*) echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'` exit 0 ;; *:Linux:*:*) # uname on the ARM produces all sorts of strangeness, and we need to # filter it out. case "$UNAME_MACHINE" in arm* | sa110*) UNAME_MACHINE="arm" ;; esac # The BFD linker knows what the default object file format is, so # first see if it will tell us. ld_help_string=`ld --help 2>&1` ld_supported_emulations=`echo $ld_help_string \ | sed -ne '/supported emulations:/!d s/[ ][ ]*/ /g s/.*supported emulations: *// s/ .*// p'` case "$ld_supported_emulations" in i?86linux) echo "${UNAME_MACHINE}-pc-linux-gnuaout" ; exit 0 ;; i?86coff) echo "${UNAME_MACHINE}-pc-linux-gnucoff" ; exit 0 ;; sparclinux) echo "${UNAME_MACHINE}-unknown-linux-gnuaout" ; exit 0 ;; armlinux) echo "${UNAME_MACHINE}-unknown-linux-gnuaout" ; exit 0 ;; m68klinux) echo "${UNAME_MACHINE}-unknown-linux-gnuaout" ; exit 0 ;; elf32ppc) echo "powerpc-unknown-linux-gnu" ; exit 0 ;; esac if test "${UNAME_MACHINE}" = "alpha" ; then sed 's/^ //' <dummy.s .globl main .ent main main: .frame \$30,0,\$26,0 .prologue 0 .long 0x47e03d80 # implver $0 lda \$2,259 .long 0x47e20c21 # amask $2,$1 srl \$1,8,\$2 sll \$2,2,\$2 sll \$0,3,\$0 addl \$1,\$0,\$0 addl \$2,\$0,\$0 ret \$31,(\$26),1 .end main EOF LIBC="" ${CC-cc} dummy.s -o dummy 2>/dev/null if test "$?" = 0 ; then ./dummy case "$?" in 7) UNAME_MACHINE="alpha" ;; 15) UNAME_MACHINE="alphaev5" ;; 14) UNAME_MACHINE="alphaev56" ;; 10) UNAME_MACHINE="alphapca56" ;; 16) UNAME_MACHINE="alphaev6" ;; esac objdump --private-headers dummy | \ grep ld.so.1 > /dev/null if test "$?" = 0 ; then LIBC="libc1" fi fi rm -f dummy.s dummy echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC} ; exit 0 elif test "${UNAME_MACHINE}" = "mips" ; then cat >dummy.c </dev/null && ./dummy "${UNAME_MACHINE}" && rm dummy.c dummy && exit 0 rm -f dummy.c dummy else # Either a pre-BFD a.out linker (linux-gnuoldld) # or one that does not give us useful --help. # GCC wants to distinguish between linux-gnuoldld and linux-gnuaout. # If ld does not provide *any* "supported emulations:" # that means it is gnuoldld. echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations:" test $? != 0 && echo "${UNAME_MACHINE}-pc-linux-gnuoldld" && exit 0 case "${UNAME_MACHINE}" in i?86) VENDOR=pc; ;; *) VENDOR=unknown; ;; esac # Determine whether the default compiler is a.out or elf cat >dummy.c < main(argc, argv) int argc; char *argv[]; { #ifdef __ELF__ # ifdef __GLIBC__ # if __GLIBC__ >= 2 printf ("%s-${VENDOR}-linux-gnu\n", argv[1]); # else printf ("%s-${VENDOR}-linux-gnulibc1\n", argv[1]); # endif # else printf ("%s-${VENDOR}-linux-gnulibc1\n", argv[1]); # endif #else printf ("%s-${VENDOR}-linux-gnuaout\n", argv[1]); #endif return 0; } EOF ${CC-cc} dummy.c -o dummy 2>/dev/null && ./dummy "${UNAME_MACHINE}" && rm dummy.c dummy && exit 0 rm -f dummy.c dummy fi ;; # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. earlier versions # are messed up and put the nodename in both sysname and nodename. i?86:DYNIX/ptx:4*:*) echo i386-sequent-sysv4 exit 0 ;; i?86:UNIX_SV:4.2MP:2.*) # Unixware is an offshoot of SVR4, but it has its own version # number series starting with 2... # I am not positive that other SVR4 systems won't match this, # I just have to hope. -- rms. # Use sysv4.2uw... so that sysv4* matches it. echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION} exit 0 ;; i?86:*:4.*:* | i?86:SYSTEM_V:4.*:*) if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then echo ${UNAME_MACHINE}-univel-sysv${UNAME_RELEASE} else echo ${UNAME_MACHINE}-pc-sysv${UNAME_RELEASE} fi exit 0 ;; i?86:*:3.2:*) if test -f /usr/options/cb.name; then UNAME_REL=`sed -n 's/.*Version //p' /dev/null >/dev/null ; then UNAME_REL=`(/bin/uname -X|egrep Release|sed -e 's/.*= //')` (/bin/uname -X|egrep i80486 >/dev/null) && UNAME_MACHINE=i486 (/bin/uname -X|egrep '^Machine.*Pentium' >/dev/null) \ && UNAME_MACHINE=i586 echo ${UNAME_MACHINE}-pc-sco$UNAME_REL else echo ${UNAME_MACHINE}-pc-sysv32 fi exit 0 ;; pc:*:*:*) # uname -m prints for DJGPP always 'pc', but it prints nothing about # the processor, so we play safe by assuming i386. echo i386-pc-msdosdjgpp exit 0 ;; Intel:Mach:3*:*) echo i386-pc-mach3 exit 0 ;; paragon:*:*:*) echo i860-intel-osf1 exit 0 ;; i860:*:4.*:*) # i860-SVR4 if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4 else # Add other i860-SVR4 vendors below as they are discovered. echo i860-unknown-sysv${UNAME_RELEASE} # Unknown i860-SVR4 fi exit 0 ;; mini*:CTIX:SYS*5:*) # "miniframe" echo m68010-convergent-sysv exit 0 ;; M68*:*:R3V[567]*:*) test -r /sysV68 && echo 'm68k-motorola-sysv' && exit 0 ;; 3[34]??:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 4850:*:4.0:3.0) OS_REL='' test -r /etc/.relid \ && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ && echo i486-ncr-sysv4.3${OS_REL} && exit 0 /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ && echo i586-ncr-sysv4.3${OS_REL} && exit 0 ;; 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ && echo i486-ncr-sysv4 && exit 0 ;; m68*:LynxOS:2.*:*) echo m68k-unknown-lynxos${UNAME_RELEASE} exit 0 ;; mc68030:UNIX_System_V:4.*:*) echo m68k-atari-sysv4 exit 0 ;; i?86:LynxOS:2.*:*) echo i386-unknown-lynxos${UNAME_RELEASE} exit 0 ;; TSUNAMI:LynxOS:2.*:*) echo sparc-unknown-lynxos${UNAME_RELEASE} exit 0 ;; rs6000:LynxOS:2.*:* | PowerPC:LynxOS:2.*:*) echo rs6000-unknown-lynxos${UNAME_RELEASE} exit 0 ;; SM[BE]S:UNIX_SV:*:*) echo mips-dde-sysv${UNAME_RELEASE} exit 0 ;; RM*:SINIX-*:*:*) echo mips-sni-sysv4 exit 0 ;; *:SINIX-*:*:*) if uname -p 2>/dev/null >/dev/null ; then UNAME_MACHINE=`(uname -p) 2>/dev/null` echo ${UNAME_MACHINE}-sni-sysv4 else echo ns32k-sni-sysv fi exit 0 ;; PENTIUM:CPunix:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort # says echo i586-unisys-sysv4 exit 0 ;; *:UNIX_System_V:4*:FTX*) # From Gerald Hewes . # How about differentiating between stratus architectures? -djm echo hppa1.1-stratus-sysv4 exit 0 ;; *:*:*:FTX*) # From seanf@swdc.stratus.com. echo i860-stratus-sysv4 exit 0 ;; mc68*:A/UX:*:*) echo m68k-apple-aux${UNAME_RELEASE} exit 0 ;; news*:NEWS-OS:*:6*) echo mips-sony-newsos6 exit 0 ;; R3000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R4000:UNIX_SV:*:*) if [ -d /usr/nec ]; then echo mips-nec-sysv${UNAME_RELEASE} else echo mips-unknown-sysv${UNAME_RELEASE} fi exit 0 ;; BeBox:BeOS:*:*) # BeOS running on hardware made by Be, PPC only. echo powerpc-be-beos exit 0 ;; BeMac:BeOS:*:*) # BeOS running on Mac or Mac clone, PPC only. echo powerpc-apple-beos exit 0 ;; BePC:BeOS:*:*) # BeOS running on Intel PC compatible. echo i586-pc-beos exit 0 ;; esac #echo '(No uname command or uname output not recognized.)' 1>&2 #echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2 cat >dummy.c < # include #endif main () { #if defined (sony) #if defined (MIPSEB) /* BFD wants "bsd" instead of "newsos". Perhaps BFD should be changed, I don't know.... */ printf ("mips-sony-bsd\n"); exit (0); #else #include printf ("m68k-sony-newsos%s\n", #ifdef NEWSOS4 "4" #else "" #endif ); exit (0); #endif #endif #if defined (__arm) && defined (__acorn) && defined (__unix) printf ("arm-acorn-riscix"); exit (0); #endif #if defined (hp300) && !defined (hpux) printf ("m68k-hp-bsd\n"); exit (0); #endif #if defined (NeXT) #if !defined (__ARCHITECTURE__) #define __ARCHITECTURE__ "m68k" #endif int version; version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`; printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version); exit (0); #endif #if defined (MULTIMAX) || defined (n16) #if defined (UMAXV) printf ("ns32k-encore-sysv\n"); exit (0); #else #if defined (CMU) printf ("ns32k-encore-mach\n"); exit (0); #else printf ("ns32k-encore-bsd\n"); exit (0); #endif #endif #endif #if defined (__386BSD__) printf ("i386-pc-bsd\n"); exit (0); #endif #if defined (sequent) #if defined (i386) printf ("i386-sequent-dynix\n"); exit (0); #endif #if defined (ns32000) printf ("ns32k-sequent-dynix\n"); exit (0); #endif #endif #if defined (_SEQUENT_) struct utsname un; uname(&un); if (strncmp(un.version, "V2", 2) == 0) { printf ("i386-sequent-ptx2\n"); exit (0); } if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */ printf ("i386-sequent-ptx1\n"); exit (0); } printf ("i386-sequent-ptx\n"); exit (0); #endif #if defined (vax) #if !defined (ultrix) printf ("vax-dec-bsd\n"); exit (0); #else printf ("vax-dec-ultrix\n"); exit (0); #endif #endif #if defined (alliant) && defined (i860) printf ("i860-alliant-bsd\n"); exit (0); #endif exit (1); } EOF ${CC-cc} dummy.c -o dummy 2>/dev/null && ./dummy && rm dummy.c dummy && exit 0 rm -f dummy.c dummy # Apollos put the system type in the environment. test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit 0; } # Convex versions that predate uname can use getsysinfo(1) if [ -x /usr/convex/getsysinfo ] then case `getsysinfo -f cpu_type` in c1*) echo c1-convex-bsd exit 0 ;; c2*) if getsysinfo -f scalar_acc then echo c32-convex-bsd else echo c2-convex-bsd fi exit 0 ;; c34*) echo c34-convex-bsd exit 0 ;; c38*) echo c38-convex-bsd exit 0 ;; c4*) echo c4-convex-bsd exit 0 ;; esac fi #echo '(Unable to guess system type)' 1>&2 exit 1 ocamlweb-1.41/support/config.sub0000755000246300004300000004655413422556307016305 0ustar filliatrvals#! /bin/sh # Configuration validation subroutine script, version 1.1. # Copyright (C) 1991, 92-97, 1998 Free Software Foundation, Inc. # This file is (in principle) common to ALL GNU software. # The presence of a machine in this file suggests that SOME GNU software # can handle that machine. It does not imply ALL GNU software can. # # This file is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, # Boston, MA 02111-1307, USA. # As a special exception to the GNU General Public License, if you # distribute this file as part of a program that contains a # configuration script generated by Autoconf, you may include it under # the same distribution terms that you use for the rest of that program. # Configuration subroutine to validate and canonicalize a configuration type. # Supply the specified configuration type as an argument. # If it is invalid, we print an error message on stderr and exit with code 1. # Otherwise, we print the canonical config type on stdout and succeed. # This file is supposed to be the same for all GNU packages # and recognize all the CPU types, system types and aliases # that are meaningful with *any* GNU software. # Each package is responsible for reporting which valid configurations # it does not support. The user should be able to distinguish # a failure to support a valid configuration from a meaningless # configuration. # The goal of this file is to map all the various variations of a given # machine specification into a single specification in the form: # CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM # or in some cases, the newer four-part form: # CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM # It is wrong to echo any other type of specification. if [ x$1 = x ] then echo Configuration name missing. 1>&2 echo "Usage: $0 CPU-MFR-OPSYS" 1>&2 echo "or $0 ALIAS" 1>&2 echo where ALIAS is a recognized configuration type. 1>&2 exit 1 fi # First pass through any local machine types. case $1 in *local*) echo $1 exit 0 ;; *) ;; esac # Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any). # Here we must recognize all the valid KERNEL-OS combinations. maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'` case $maybe_os in linux-gnu*) os=-$maybe_os basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'` ;; *) basic_machine=`echo $1 | sed 's/-[^-]*$//'` if [ $basic_machine != $1 ] then os=`echo $1 | sed 's/.*-/-/'` else os=; fi ;; esac ### Let's recognize common machines as not being operating systems so ### that things like config.sub decstation-3100 work. We also ### recognize some manufacturers as not being operating systems, so we ### can provide default operating systems below. case $os in -sun*os*) # Prevent following clause from handling this invalid input. ;; -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \ -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \ -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \ -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\ -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \ -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \ -apple) os= basic_machine=$1 ;; -hiux*) os=-hiuxwe2 ;; -sco5) os=sco3.2v5 basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -sco4) os=-sco3.2v4 basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -sco3.2.[4-9]*) os=`echo $os | sed -e 's/sco3.2./sco3.2v/'` basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -sco3.2v[4-9]*) # Don't forget version if it is 3.2v4 or newer. basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -sco*) os=-sco3.2v2 basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -isc) os=-isc2.2 basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -clix*) basic_machine=clipper-intergraph ;; -isc*) basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; -lynx*) os=-lynxos ;; -ptx*) basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'` ;; -windowsnt*) os=`echo $os | sed -e 's/windowsnt/winnt/'` ;; -psos*) os=-psos ;; esac # Decode aliases for certain CPU-COMPANY combinations. case $basic_machine in # Recognize the basic CPU types without company name. # Some are omitted here because they have special meanings below. tahoe | i860 | m32r | m68k | m68000 | m88k | ns32k | arc | arm \ | arme[lb] | pyramid | mn10200 | mn10300 \ | tron | a29k | 580 | i960 | h8300 | hppa | hppa1.0 | hppa1.1 \ | hppa2.0 \ | alpha | alphaev5 | alphaev56 | we32k | ns16k | clipper \ | i370 | sh | powerpc | powerpcle | 1750a | dsp16xx | pdp11 \ | mips64 | mipsel | mips64el | mips64orion | mips64orionel \ | mipstx39 | mipstx39el \ | sparc | sparclet | sparclite | sparc64 | v850) basic_machine=$basic_machine-unknown ;; # We use `pc' rather than `unknown' # because (1) that's what they normally are, and # (2) the word "unknown" tends to confuse beginning users. i[34567]86) basic_machine=$basic_machine-pc ;; # Object if more than one company name word. *-*-*) echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 exit 1 ;; # Recognize the basic CPU types with company name. vax-* | tahoe-* | i[34567]86-* | i860-* | m32r-* | m68k-* | m68000-* \ | m88k-* | sparc-* | ns32k-* | fx80-* | arc-* | arm-* | c[123]* \ | mips-* | pyramid-* | tron-* | a29k-* | romp-* | rs6000-* \ | power-* | none-* | 580-* | cray2-* | h8300-* | i960-* \ | xmp-* | ymp-* | hppa-* | hppa1.0-* | hppa1.1-* | hppa2.0-* \ | alpha-* | alphaev5-* | alphaev56-* | we32k-* | cydra-* \ | ns16k-* | pn-* | np1-* | xps100-* | clipper-* | orion-* \ | sparclite-* | pdp11-* | sh-* | powerpc-* | powerpcle-* \ | sparc64-* | mips64-* | mipsel-* \ | mips64el-* | mips64orion-* | mips64orionel-* \ | mipstx39-* | mipstx39el-* \ | f301-*) ;; # Recognize the various machine names and aliases which stand # for a CPU type and a company and sometimes even an OS. 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc) basic_machine=m68000-att ;; 3b*) basic_machine=we32k-att ;; alliant | fx80) basic_machine=fx80-alliant ;; altos | altos3068) basic_machine=m68k-altos ;; am29k) basic_machine=a29k-none os=-bsd ;; amdahl) basic_machine=580-amdahl os=-sysv ;; amiga | amiga-*) basic_machine=m68k-cbm ;; amigaos | amigados) basic_machine=m68k-cbm os=-amigaos ;; amigaunix | amix) basic_machine=m68k-cbm os=-sysv4 ;; apollo68) basic_machine=m68k-apollo os=-sysv ;; aux) basic_machine=m68k-apple os=-aux ;; balance) basic_machine=ns32k-sequent os=-dynix ;; convex-c1) basic_machine=c1-convex os=-bsd ;; convex-c2) basic_machine=c2-convex os=-bsd ;; convex-c32) basic_machine=c32-convex os=-bsd ;; convex-c34) basic_machine=c34-convex os=-bsd ;; convex-c38) basic_machine=c38-convex os=-bsd ;; cray | ymp) basic_machine=ymp-cray os=-unicos ;; cray2) basic_machine=cray2-cray os=-unicos ;; [ctj]90-cray) basic_machine=c90-cray os=-unicos ;; crds | unos) basic_machine=m68k-crds ;; da30 | da30-*) basic_machine=m68k-da30 ;; decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn) basic_machine=mips-dec ;; delta | 3300 | motorola-3300 | motorola-delta \ | 3300-motorola | delta-motorola) basic_machine=m68k-motorola ;; delta88) basic_machine=m88k-motorola os=-sysv3 ;; dpx20 | dpx20-*) basic_machine=rs6000-bull os=-bosx ;; dpx2* | dpx2*-bull) basic_machine=m68k-bull os=-sysv3 ;; ebmon29k) basic_machine=a29k-amd os=-ebmon ;; elxsi) basic_machine=elxsi-elxsi os=-bsd ;; encore | umax | mmax) basic_machine=ns32k-encore ;; fx2800) basic_machine=i860-alliant ;; genix) basic_machine=ns32k-ns ;; gmicro) basic_machine=tron-gmicro os=-sysv ;; h3050r* | hiux*) basic_machine=hppa1.1-hitachi os=-hiuxwe2 ;; h8300hms) basic_machine=h8300-hitachi os=-hms ;; harris) basic_machine=m88k-harris os=-sysv3 ;; hp300-*) basic_machine=m68k-hp ;; hp300bsd) basic_machine=m68k-hp os=-bsd ;; hp300hpux) basic_machine=m68k-hp os=-hpux ;; hp9k2[0-9][0-9] | hp9k31[0-9]) basic_machine=m68000-hp ;; hp9k3[2-9][0-9]) basic_machine=m68k-hp ;; hp9k7[0-9][0-9] | hp7[0-9][0-9] | hp9k8[0-9]7 | hp8[0-9]7) basic_machine=hppa1.1-hp ;; hp9k8[0-9][0-9] | hp8[0-9][0-9]) basic_machine=hppa1.0-hp ;; hppa-next) os=-nextstep3 ;; i370-ibm* | ibm*) basic_machine=i370-ibm os=-mvs ;; # I'm not sure what "Sysv32" means. Should this be sysv3.2? i[34567]86v32) basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` os=-sysv32 ;; i[34567]86v4*) basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` os=-sysv4 ;; i[34567]86v) basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` os=-sysv ;; i[34567]86sol2) basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` os=-solaris2 ;; iris | iris4d) basic_machine=mips-sgi case $os in -irix*) ;; *) os=-irix4 ;; esac ;; isi68 | isi) basic_machine=m68k-isi os=-sysv ;; m88k-omron*) basic_machine=m88k-omron ;; magnum | m3230) basic_machine=mips-mips os=-sysv ;; merlin) basic_machine=ns32k-utek os=-sysv ;; miniframe) basic_machine=m68000-convergent ;; mipsel*-linux*) basic_machine=mipsel-unknown os=-linux-gnu ;; mips*-linux*) basic_machine=mips-unknown os=-linux-gnu ;; mips3*-*) basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'` ;; mips3*) basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown ;; ncr3000) basic_machine=i486-ncr os=-sysv4 ;; news | news700 | news800 | news900) basic_machine=m68k-sony os=-newsos ;; news1000) basic_machine=m68030-sony os=-newsos ;; news-3600 | risc-news) basic_machine=mips-sony os=-newsos ;; next | m*-next ) basic_machine=m68k-next case $os in -nextstep* ) ;; -ns2*) os=-nextstep2 ;; *) os=-nextstep3 ;; esac ;; nh3000) basic_machine=m68k-harris os=-cxux ;; nh[45]000) basic_machine=m88k-harris os=-cxux ;; nindy960) basic_machine=i960-intel os=-nindy ;; np1) basic_machine=np1-gould ;; pa-hitachi) basic_machine=hppa1.1-hitachi os=-hiuxwe2 ;; paragon) basic_machine=i860-intel os=-osf ;; pbd) basic_machine=sparc-tti ;; pbb) basic_machine=m68k-tti ;; pc532 | pc532-*) basic_machine=ns32k-pc532 ;; pentium | p5 | k5 | nexen) basic_machine=i586-pc ;; pentiumpro | p6 | k6 | 6x86) basic_machine=i686-pc ;; pentiumii | pentium2) basic_machine=i786-pc ;; pentium-* | p5-* | k5-* | nexen-*) basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'` ;; pentiumpro-* | p6-* | k6-* | 6x86-*) basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'` ;; pentiumii-* | pentium2-*) basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'` ;; pn) basic_machine=pn-gould ;; power) basic_machine=rs6000-ibm ;; ppc) basic_machine=powerpc-unknown ;; ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` ;; ppcle | powerpclittle | ppc-le | powerpc-little) basic_machine=powerpcle-unknown ;; ppcle-* | powerpclittle-*) basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'` ;; ps2) basic_machine=i386-ibm ;; rm[46]00) basic_machine=mips-siemens ;; rtpc | rtpc-*) basic_machine=romp-ibm ;; sequent) basic_machine=i386-sequent ;; sh) basic_machine=sh-hitachi os=-hms ;; sps7) basic_machine=m68k-bull os=-sysv2 ;; spur) basic_machine=spur-unknown ;; sun2) basic_machine=m68000-sun ;; sun2os3) basic_machine=m68000-sun os=-sunos3 ;; sun2os4) basic_machine=m68000-sun os=-sunos4 ;; sun3os3) basic_machine=m68k-sun os=-sunos3 ;; sun3os4) basic_machine=m68k-sun os=-sunos4 ;; sun4os3) basic_machine=sparc-sun os=-sunos3 ;; sun4os4) basic_machine=sparc-sun os=-sunos4 ;; sun4sol2) basic_machine=sparc-sun os=-solaris2 ;; sun3 | sun3-*) basic_machine=m68k-sun ;; sun4) basic_machine=sparc-sun ;; sun386 | sun386i | roadrunner) basic_machine=i386-sun ;; symmetry) basic_machine=i386-sequent os=-dynix ;; tx39) basic_machine=mipstx39-unknown ;; tx39el) basic_machine=mipstx39el-unknown ;; tower | tower-32) basic_machine=m68k-ncr ;; udi29k) basic_machine=a29k-amd os=-udi ;; ultra3) basic_machine=a29k-nyu os=-sym1 ;; vaxv) basic_machine=vax-dec os=-sysv ;; vms) basic_machine=vax-dec os=-vms ;; vpp*|vx|vx-*) basic_machine=f301-fujitsu ;; vxworks960) basic_machine=i960-wrs os=-vxworks ;; vxworks68) basic_machine=m68k-wrs os=-vxworks ;; vxworks29k) basic_machine=a29k-wrs os=-vxworks ;; xmp) basic_machine=xmp-cray os=-unicos ;; xps | xps100) basic_machine=xps100-honeywell ;; none) basic_machine=none-none os=-none ;; # Here we handle the default manufacturer of certain CPU types. It is in # some cases the only manufacturer, in others, it is the most popular. mips) if [ x$os = x-linux-gnu ]; then basic_machine=mips-unknown else basic_machine=mips-mips fi ;; romp) basic_machine=romp-ibm ;; rs6000) basic_machine=rs6000-ibm ;; vax) basic_machine=vax-dec ;; pdp11) basic_machine=pdp11-dec ;; we32k) basic_machine=we32k-att ;; sparc) basic_machine=sparc-sun ;; cydra) basic_machine=cydra-cydrome ;; orion) basic_machine=orion-highlevel ;; orion105) basic_machine=clipper-highlevel ;; *) echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 exit 1 ;; esac # Here we canonicalize certain aliases for manufacturers. case $basic_machine in *-digital*) basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'` ;; *-commodore*) basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'` ;; *) ;; esac # Decode manufacturer-specific aliases for certain operating systems. if [ x"$os" != x"" ] then case $os in # First match some system type aliases # that might get confused with valid system types. # -solaris* is a basic system type, with this one exception. -solaris1 | -solaris1.*) os=`echo $os | sed -e 's|solaris1|sunos4|'` ;; -solaris) os=-solaris2 ;; -svr4*) os=-sysv4 ;; -unixware*) os=-sysv4.2uw ;; -gnu/linux*) os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'` ;; # First accept the basic system types. # The portable systems comes first. # Each alternative MUST END IN A *, to match a version number. # -sysv* is not here because it comes later, after sysvr4. -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \ | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\ | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \ | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \ | -aos* \ | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \ | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \ | -hiux* | -386bsd* | -netbsd* | -openbsd* | -freebsd* | -riscix* \ | -lynxos* | -bosx* | -nextstep* | -cxux* | -aout* | -elf* \ | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \ | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \ | -cygwin32* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ | -mingw32* | -linux-gnu* | -uxpv* | -beos*) # Remember, each alternative MUST END IN *, to match a version number. ;; -linux*) os=`echo $os | sed -e 's|linux|linux-gnu|'` ;; -sunos5*) os=`echo $os | sed -e 's|sunos5|solaris2|'` ;; -sunos6*) os=`echo $os | sed -e 's|sunos6|solaris3|'` ;; -osfrose*) os=-osfrose ;; -osf*) os=-osf ;; -utek*) os=-bsd ;; -dynix*) os=-bsd ;; -acis*) os=-aos ;; -ctix* | -uts*) os=-sysv ;; -ns2 ) os=-nextstep2 ;; # Preserve the version number of sinix5. -sinix5.*) os=`echo $os | sed -e 's|sinix|sysv|'` ;; -sinix*) os=-sysv4 ;; -triton*) os=-sysv3 ;; -oss*) os=-sysv3 ;; -svr4) os=-sysv4 ;; -svr3) os=-sysv3 ;; -sysvr4) os=-sysv4 ;; # This must come after -sysvr4. -sysv*) ;; -xenix) os=-xenix ;; -none) ;; *) # Get rid of the `-' at the beginning of $os. os=`echo $os | sed 's/[^-]*-//'` echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2 exit 1 ;; esac else # Here we handle the default operating systems that come with various machines. # The value should be what the vendor currently ships out the door with their # machine or put another way, the most popular os provided with the machine. # Note that if you're going to try to match "-MANUFACTURER" here (say, # "-sun"), then you have to tell the case statement up towards the top # that MANUFACTURER isn't an operating system. Otherwise, code above # will signal an error saying that MANUFACTURER isn't an operating # system, and we'll never get to this point. case $basic_machine in *-acorn) os=-riscix1.2 ;; arm*-semi) os=-aout ;; pdp11-*) os=-none ;; *-dec | vax-*) os=-ultrix4.2 ;; m68*-apollo) os=-domain ;; i386-sun) os=-sunos4.0.2 ;; m68000-sun) os=-sunos3 # This also exists in the configure program, but was not the # default. # os=-sunos4 ;; *-tti) # must be before sparc entry or we get the wrong os. os=-sysv3 ;; sparc-* | *-sun) os=-sunos4.1.1 ;; *-be) os=-beos ;; *-ibm) os=-aix ;; *-hp) os=-hpux ;; *-hitachi) os=-hiux ;; i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent) os=-sysv ;; *-cbm) os=-amigaos ;; *-dg) os=-dgux ;; *-dolphin) os=-sysv3 ;; m68k-ccur) os=-rtu ;; m88k-omron*) os=-luna ;; *-next ) os=-nextstep ;; *-sequent) os=-ptx ;; *-crds) os=-unos ;; *-ns) os=-genix ;; i370-*) os=-mvs ;; *-next) os=-nextstep3 ;; *-gould) os=-sysv ;; *-highlevel) os=-bsd ;; *-encore) os=-bsd ;; *-sgi) os=-irix ;; *-siemens) os=-sysv4 ;; *-masscomp) os=-rtu ;; f301-fujitsu) os=-uxpv ;; *) os=-none ;; esac fi # Here we handle the case where we know the os, and the CPU type, but not the # manufacturer. We pick the logical manufacturer. vendor=unknown case $basic_machine in *-unknown) case $os in -riscix*) vendor=acorn ;; -sunos*) vendor=sun ;; -aix*) vendor=ibm ;; -hpux*) vendor=hp ;; -hiux*) vendor=hitachi ;; -unos*) vendor=crds ;; -dgux*) vendor=dg ;; -luna*) vendor=omron ;; -genix*) vendor=ns ;; -mvs*) vendor=ibm ;; -ptx*) vendor=sequent ;; -vxsim* | -vxworks*) vendor=wrs ;; -aux*) vendor=apple ;; esac basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"` ;; esac echo $basic_machine$os ocamlweb-1.41/support/install-sh0000755000246300004300000001256213422556307016316 0ustar filliatrvals#! /bin/sh # # install - install a program, script, or datafile # This comes from X11R5 (mit/util/scripts/install.sh). # # Copyright 1991 by the Massachusetts Institute of Technology # # Permission to use, copy, modify, distribute, and sell this software and its # documentation for any purpose is hereby granted without fee, provided that # the above copyright notice appear in all copies and that both that # copyright notice and this permission notice appear in supporting # documentation, and that the name of M.I.T. not be used in advertising or # publicity pertaining to distribution of the software without specific, # written prior permission. M.I.T. makes no representations about the # suitability of this software for any purpose. It is provided "as is" # without express or implied warranty. # # Calling this script install-sh is preferred over install.sh, to prevent # `make' implicit rules from creating a file called install from it # when there is no Makefile. # # This script is compatible with the BSD install script, but was written # from scratch. # # set DOITPROG to echo to test this script # Don't use :- since 4.3BSD and earlier shells don't like it. doit="${DOITPROG-}" # put in absolute paths if you don't have them in your path; or use env. vars. mvprog="${MVPROG-mv}" cpprog="${CPPROG-cp}" chmodprog="${CHMODPROG-chmod}" chownprog="${CHOWNPROG-chown}" chgrpprog="${CHGRPPROG-chgrp}" stripprog="${STRIPPROG-strip}" rmprog="${RMPROG-rm}" mkdirprog="${MKDIRPROG-mkdir}" transformbasename="" transform_arg="" instcmd="$mvprog" chmodcmd="$chmodprog 0755" chowncmd="" chgrpcmd="" stripcmd="" rmcmd="$rmprog -f" mvcmd="$mvprog" src="" dst="" dir_arg="" while [ x"$1" != x ]; do case $1 in -c) instcmd="$cpprog" shift continue;; -d) dir_arg=true shift continue;; -m) chmodcmd="$chmodprog $2" shift shift continue;; -o) chowncmd="$chownprog $2" shift shift continue;; -g) chgrpcmd="$chgrpprog $2" shift shift continue;; -s) stripcmd="$stripprog" shift continue;; -t=*) transformarg=`echo $1 | sed 's/-t=//'` shift continue;; -b=*) transformbasename=`echo $1 | sed 's/-b=//'` shift continue;; *) if [ x"$src" = x ] then src=$1 else # this colon is to work around a 386BSD /bin/sh bug : dst=$1 fi shift continue;; esac done if [ x"$src" = x ] then echo "install: no input file specified" exit 1 else true fi if [ x"$dir_arg" != x ]; then dst=$src src="" if [ -d $dst ]; then instcmd=: else instcmd=mkdir fi else # Waiting for this to be detected by the "$instcmd $src $dsttmp" command # might cause directories to be created, which would be especially bad # if $src (and thus $dsttmp) contains '*'. if [ -f $src -o -d $src ] then true else echo "install: $src does not exist" exit 1 fi if [ x"$dst" = x ] then echo "install: no destination specified" exit 1 else true fi # If destination is a directory, append the input filename; if your system # does not like double slashes in filenames, you may need to add some logic if [ -d $dst ] then dst="$dst"/`basename $src` else true fi fi ## this sed command emulates the dirname command dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` # Make sure that the destination directory exists. # this part is taken from Noah Friedman's mkinstalldirs script # Skip lots of stat calls in the usual case. if [ ! -d "$dstdir" ]; then defaultIFS=' ' IFS="${IFS-${defaultIFS}}" oIFS="${IFS}" # Some sh's can't handle IFS=/ for some reason. IFS='%' set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` IFS="${oIFS}" pathcomp='' while [ $# -ne 0 ] ; do pathcomp="${pathcomp}${1}" shift if [ ! -d "${pathcomp}" ] ; then $mkdirprog "${pathcomp}" else true fi pathcomp="${pathcomp}/" done fi if [ x"$dir_arg" != x ] then $doit $instcmd $dst && if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi else # If we're going to rename the final executable, determine the name now. if [ x"$transformarg" = x ] then dstfile=`basename $dst` else dstfile=`basename $dst $transformbasename | sed $transformarg`$transformbasename fi # don't allow the sed command to completely eliminate the filename if [ x"$dstfile" = x ] then dstfile=`basename $dst` else true fi # Make a temp file name in the proper directory. dsttmp=$dstdir/#inst.$$# # Move or copy the file name to the temp name $doit $instcmd $src $dsttmp && trap "rm -f ${dsttmp}" 0 && # and set any options; do chmod last to preserve setuid bits # If any of these fail, we abort the whole thing. If we want to # ignore errors from any of these, just make sure not to ignore # errors from the above "$doit $instcmd $src $dsttmp" command. if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && # Now rename the file to the real destination. $doit $rmcmd -f $dstdir/$dstfile && $doit $mvcmd $dsttmp $dstdir/$dstfile fi && exit 0 ocamlweb-1.41/cross.ml0000644000246300004300000005626513422556306014270 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*i*) open Lexing open Filename open Location open Longident open Output open Printf open Asttypes open Parsetree (*i*) (*s Cross references inside Caml files are kept in the following two global tables, which keep the places where things are defined and used, to produce the final indexes. *) type where = { w_filename : string; w_loc : int } module Whereset = Set.Make(struct type t = where let compare = compare end) type entry_type = | Value | Constructor | Field | Label | Type | Exception | Module | ModuleType | Class | Method | LexParseRule (*r CAMLLEX entry points *) | RegExpr (*r CAMLLEX regular expressions *) | YaccNonTerminal (*r CAMLYACC non-terminal symbols *) | YaccTerminal (*r CAMLYACC terminal symbols, i.e. tokens *) type index_entry = { e_name : string; e_type : entry_type } module Idmap = Map.Make(struct type t = index_entry let compare = compare end) let defined = ref Idmap.empty let used = ref Idmap.empty (*s The function [add_global] is a generic function to add an entry in one table. [add_def] is used to add the definition of an identifier (so in the table [defined]). *) let add_global table k i = try let s = Idmap.find k !table in table := Idmap.add k (Whereset.add i s) !table with Not_found -> table := Idmap.add k (Whereset.singleton i) !table let current_file = ref "" let current_offset = ref 0 let current_location loc = { w_filename = !current_file; w_loc = !current_offset + loc.loc_start.pos_cnum } let add_def loc t s = if String.length s > 0 then let e = { e_name = s; e_type = t } in add_global defined e (current_location loc) (*s Another table, [locals], keeps the bound variables, in order to distinguish them from global identifiers. Then the function [add_uses] registers that an identifier is used (in the table [used]), taking care of the fact that it is not a bound variable (in the table [locals]). [add_uses_q] iters [add_uses] on a qualified identifier. *) module Stringset = Set.Make(struct type t = string let compare = compare end) let locals = ref Stringset.empty let reset_cross f offs = assert (Stringset.cardinal !locals = 0); locals := Stringset.empty; current_file := f; current_offset := offs let add_local s = locals := Stringset.add s !locals let is_uppercase = function 'A'..'Z' -> true | _ -> false let add_uses loc t s = if String.length s > 0 && not (is_keyword s) && not (Stringset.mem s !locals) then let e = { e_name = s; e_type = t } in add_global used e (current_location loc) let add_uses_q loc t q = let rec addmod = function | Lident s -> add_uses loc Module s | Ldot (q,s) -> addmod q; add_uses loc Module s | Lapply (q1,q2) -> addmod q1; addmod q2 in match q with | Lident s -> add_uses loc t s | Ldot (q,s) -> addmod q; add_uses loc t s | Lapply (q1,q2) -> addmod q1; addmod q2 (*s Some useful functions. *) let iter_fst f = List.iter (fun x -> f (fst x)) let iter_snd f = List.iter (fun x -> f (snd x)) let option_iter f = function None -> () | Some x -> f x (*s When traversing a pattern, we must collect all its identifiers, in order to declare them as bound variables (or definitions behind a \textsf{let} construction). That is the job of the function [ids_of_a_pattern]. Then [pattern_for_def] declares all the identifiers of a pattern as new definitions. *) let ids_of_a_pattern p = let r = ref [] in let add id = r := id :: !r in let rec pattern_d = function | Ppat_any -> () | Ppat_var id -> add id | Ppat_alias (p,id) -> add id; pattern p | Ppat_constant _ -> () | Ppat_tuple pl -> List.iter pattern pl | Ppat_construct (_,po,_) -> option_iter pattern po | Ppat_record l -> iter_snd pattern l | Ppat_array pl -> List.iter pattern pl | Ppat_or (p1,p2) -> pattern p1; pattern p2 | Ppat_constraint (p,_) -> pattern p | Ppat_variant (_,po) -> option_iter pattern po | Ppat_type _ -> () and pattern p = pattern_d p.ppat_desc in pattern p; !r let pattern_for_def p = let loc = p.ppat_loc in let ids = ids_of_a_pattern p in List.iter (add_def loc Value) ids (*s The following function locally adds some given variables to the set of bound variables, during the time of the application of a given function on a given argument. *) let bind_variables ids f x = let save = !locals in List.iter add_local ids; f x; locals := save (*s \textbf{Traversing of Caml abstract syntax trees.} Each type [t] in those abstract syntax trees is associated to a function [tr_t] which traverses it, declaring the identifiers used and defined. Those types are defined in the Caml module interface [Paresetree.mli] contained in the Caml source distribution. The following code is quite code, but systematic and easy to understand. *) (*s Core types. *) let rec tr_core_type t = tr_core_type_desc t.ptyp_loc t.ptyp_desc and tr_core_type_desc loc = function | Ptyp_any | Ptyp_var _ -> () | Ptyp_arrow (l,t1,t2) -> add_def loc Label l; tr_core_type t1; tr_core_type t2 | Ptyp_tuple tl -> List.iter tr_core_type tl | Ptyp_constr (q,tl) -> add_uses_q loc Type q; List.iter tr_core_type tl | Ptyp_object l -> List.iter tr_core_field_type l | Ptyp_class (id,l,ll) -> add_uses_q loc Class id; List.iter (add_def loc Label) ll; List.iter tr_core_type l | Ptyp_alias (ct,_) -> tr_core_type ct | Ptyp_variant (l,_,_) -> List.iter tr_row_field l | Ptyp_poly (_,t) -> tr_core_type t and tr_row_field = function | Rtag (_,_,ctl) -> List.iter tr_core_type ctl | Rinherit t -> tr_core_type t and tr_core_field_type ft = tr_core_field_desc ft.pfield_loc ft.pfield_desc and tr_core_field_desc loc = function | Pfield (id,ct) -> add_uses loc Method id; tr_core_type ct | Pfield_var -> () (*s Type expressions for the class language. *) let tr_class_infos f p = add_def p.pci_loc Class p.pci_name; f p.pci_expr (*s Value expressions for the core language. *) let bind_pattern f (p,e) = bind_variables (ids_of_a_pattern p) f e let bind_patterns f pl e = let ids = List.flatten (List.map ids_of_a_pattern pl) in bind_variables ids f e let rec tr_expression e = tr_expression_desc e.pexp_loc e.pexp_desc and tr_expression_desc loc = function | Pexp_ident q -> add_uses_q loc Value q | Pexp_apply (e,lel) -> tr_expression e; List.iter (fun (l,e) -> add_uses loc Label l; tr_expression e) lel | Pexp_ifthenelse (e1,e2,e3) -> tr_expression e1; tr_expression e2; option_iter tr_expression e3 | Pexp_sequence (e1,e2) -> tr_expression e1; tr_expression e2 | Pexp_while (e1,e2) -> tr_expression e1; tr_expression e2 | Pexp_tuple el -> List.iter tr_expression el | Pexp_construct (q,e,_) -> add_uses_q loc Constructor q; option_iter tr_expression e | Pexp_function (l,eo,pel) -> add_def loc Label l; option_iter tr_expression eo; List.iter (bind_pattern tr_expression) pel | Pexp_match (e,pel) -> tr_expression e; List.iter (bind_pattern tr_expression) pel | Pexp_try (e,pel) -> tr_expression e; List.iter (bind_pattern tr_expression) pel | Pexp_let (recf,pel,e) -> let pl = List.map fst pel in if recf = Recursive then iter_snd (bind_patterns tr_expression pl) pel else iter_snd tr_expression pel; bind_patterns tr_expression pl e | Pexp_record (l,e) -> iter_fst (add_uses_q loc Field) l; iter_snd tr_expression l; option_iter tr_expression e | Pexp_field (e,q) -> tr_expression e; add_uses_q loc Field q | Pexp_setfield (e1,q,e2) -> tr_expression e1; add_uses_q loc Field q; tr_expression e2 | Pexp_array el -> List.iter tr_expression el | Pexp_for (i,e1,e2,_,e) -> tr_expression e1; tr_expression e2; bind_variables [i] tr_expression e | Pexp_constraint (e,t1,t2) -> tr_expression e; option_iter tr_core_type t1; option_iter tr_core_type t2 | Pexp_when (e1,e2) -> tr_expression e1; tr_expression e2 | Pexp_letmodule (x,m,e) -> tr_module_expr m; bind_variables [x] tr_expression e | Pexp_constant _ -> () | Pexp_send (e,id) -> add_uses loc Method id; tr_expression e | Pexp_new id -> add_uses_q loc Class id | Pexp_setinstvar (id,e) -> add_uses loc Value id; tr_expression e | Pexp_override l -> iter_fst (add_uses loc Method) l; iter_snd tr_expression l | Pexp_variant (_,eo) -> option_iter tr_expression eo | Pexp_assert e -> tr_expression e | Pexp_assertfalse -> () | Pexp_lazy e -> tr_expression e | Pexp_poly (e, t) -> tr_expression e; option_iter tr_core_type t | Pexp_object cs -> tr_class_structure cs (*s Value descriptions. *) and tr_value_description vd = tr_core_type vd.pval_type (*s Type declarations. *) and tr_type_declaration td = tr_type_kind td.ptype_loc td.ptype_kind; option_iter tr_core_type td.ptype_manifest and tr_type_kind loc = function | Ptype_abstract -> () | Ptype_variant (cl,_) -> iter_fst (add_def loc Constructor) cl; iter_snd (List.iter tr_core_type) cl | Ptype_record (fl,_) -> List.iter (fun (f,_,t) -> add_def loc Field f; tr_core_type t) fl and tr_exception_declaration ed = List.iter tr_core_type ed (*s Type expressions for the class language. *) and tr_class_type c = tr_class_type_desc c.pcty_loc c.pcty_desc and tr_class_type_desc loc = function | Pcty_constr (id,l) -> add_uses_q loc Class id; List.iter tr_core_type l | Pcty_signature cs -> tr_class_signature cs | Pcty_fun (l,co,cl) -> add_def loc Label l; tr_core_type co; tr_class_type cl and tr_class_signature (ct,l) = tr_core_type ct; List.iter tr_class_type_field l and tr_class_type_field = function | Pctf_inher ct -> tr_class_type ct | Pctf_val (id,_,ct,loc) -> add_def loc Value id; option_iter tr_core_type ct | Pctf_virt (id,_,ct,loc) -> add_def loc Method id; tr_core_type ct | Pctf_meth (id,_,ct,loc) -> add_def loc Method id; tr_core_type ct | Pctf_cstr (ct1,ct2,_) -> tr_core_type ct1; tr_core_type ct2 and tr_class_description x = tr_class_infos tr_class_type x and tr_class_type_declaration x = tr_class_infos tr_class_type x (*s Value expressions for the class language. *) and tr_class_expr ce = tr_class_expr_desc ce.pcl_loc ce.pcl_desc and tr_class_expr_desc loc = function | Pcl_constr (id,l) -> add_uses_q loc Class id; List.iter tr_core_type l | Pcl_structure cs -> tr_class_structure cs | Pcl_fun (l,eo,p,ce) -> add_def loc Label l; option_iter tr_expression eo; bind_variables (ids_of_a_pattern p) tr_class_expr ce | Pcl_apply (ce,l) -> tr_class_expr ce; List.iter (fun (l,e) -> add_uses loc Label l; tr_expression e) l | Pcl_let (recf,pel,ce) -> let pl = List.map fst pel in if recf = Recursive then iter_snd (bind_patterns tr_expression pl) pel else iter_snd tr_expression pel; bind_patterns tr_class_expr pl ce | Pcl_constraint (ce,ct) -> tr_class_expr ce; tr_class_type ct and tr_class_structure (p,l) = List.iter (fun f -> bind_pattern tr_class_field (p,f)) l and tr_class_field = function | Pcf_inher (ce,_) -> tr_class_expr ce | Pcf_val (id,_,e,loc) -> add_def loc Value id; tr_expression e | Pcf_virt(id,_,ct,loc) -> add_def loc Method id; tr_core_type ct | Pcf_meth (id,_,e,loc) -> add_def loc Method id; tr_expression e | Pcf_cstr (ct1,ct2,_) -> tr_core_type ct1; tr_core_type ct2 | Pcf_let (recf,pel,_) -> let pl = List.map fst pel in if recf = Recursive then iter_snd (bind_patterns tr_expression pl) pel else iter_snd tr_expression pel | Pcf_init e -> tr_expression e and tr_class_declaration x = tr_class_infos tr_class_expr x (*s Type expressions for the module language. *) and tr_module_type mt = tr_module_type_desc mt.pmty_loc mt.pmty_desc and tr_module_type_desc loc = function | Pmty_ident id -> add_uses_q loc ModuleType id | Pmty_signature s -> tr_signature s | Pmty_functor (id,mt1,mt2) -> tr_module_type mt1; bind_variables [id] tr_module_type mt2 | Pmty_with (mt,cl) -> tr_module_type mt; List.iter (fun (id,c) -> add_uses_q loc Type id; tr_with_constraint loc c) cl and tr_signature s = List.iter tr_signature_item s and tr_signature_item i = tr_signature_item_desc i.psig_loc i.psig_desc and tr_signature_item_desc loc = function | Psig_value (x,vd) -> add_def loc Value x; tr_value_description vd | Psig_type l -> iter_fst (add_def loc Type) l; iter_snd tr_type_declaration l | Psig_exception (id,ed) -> add_def loc Exception id; tr_exception_declaration ed | Psig_module (id,mt) -> add_def loc Module id; tr_module_type mt | Psig_recmodule l -> List.iter (fun (id,mt) -> add_def loc Module id; tr_module_type mt) l | Psig_modtype (id,mtd) -> add_def loc ModuleType id; tr_modtype_declaration mtd | Psig_open q -> add_uses_q loc Module q | Psig_include mt -> tr_module_type mt | Psig_class l -> List.iter tr_class_description l | Psig_class_type l -> List.iter tr_class_type_declaration l and tr_modtype_declaration = function | Pmodtype_abstract -> () | Pmodtype_manifest mt -> tr_module_type mt and tr_with_constraint loc = function | Pwith_type td -> tr_type_declaration td | Pwith_module id -> add_uses_q loc Module id (*s Value expressions for the module language. *) and tr_module_expr me = tr_module_expr_desc me.pmod_loc me.pmod_desc and tr_module_expr_desc loc = function | Pmod_ident id -> add_uses_q loc Module id | Pmod_structure s -> tr_structure s | Pmod_functor (id,mt,me) -> tr_module_type mt; bind_variables [id] tr_module_expr me | Pmod_apply (me1,me2) -> tr_module_expr me1; tr_module_expr me2 | Pmod_constraint (me,mt) -> tr_module_expr me; tr_module_type mt and tr_structure l = List.iter tr_structure_item l and tr_structure_item i = tr_structure_item_desc i.pstr_loc i.pstr_desc and tr_structure_item_desc loc = function | Pstr_eval e -> tr_expression e | Pstr_value (_,pel) -> iter_fst pattern_for_def pel; iter_snd tr_expression pel | Pstr_primitive (id,vd) -> add_def loc Value id; tr_value_description vd | Pstr_type l -> iter_fst (add_def loc Type) l; iter_snd tr_type_declaration l | Pstr_exception (id,ed) -> add_def loc Exception id; tr_exception_declaration ed | Pstr_module (id,me) -> add_def loc Module id; tr_module_expr me | Pstr_recmodule l -> List.iter (fun (id,mt,me) -> add_def loc Module id; tr_module_type mt; tr_module_expr me) l | Pstr_modtype (id,mt) -> add_def loc ModuleType id; tr_module_type mt | Pstr_open m -> add_uses_q loc Module m | Pstr_class l -> List.iter tr_class_declaration l | Pstr_class_type l -> List.iter tr_class_type_declaration l | Pstr_exn_rebind (id,q) -> add_def loc Exception id; add_uses_q loc Exception q | Pstr_include me -> tr_module_expr me (*s Given all that collecting functions, we can now define two functions [cross_implem] and [cross_interf] which respectively compute the cross-references in implementations and interfaces. *) let zero = { pos_fname = ""; pos_lnum = 0; pos_bol = 0; pos_cnum = 9 } let add_module m = add_def { loc_start = zero; loc_end = zero; loc_ghost = false } Module m let wrapper parsing_function traverse_function f m = reset_cross f 0; add_module m; let c = open_in f in let lexbuf = Lexing.from_channel c in try traverse_function (parsing_function lexbuf); close_in c with Syntaxerr.Error _ | Syntaxerr.Escape_error | Lexer.Error _ -> begin if not !quiet then eprintf " ** warning: syntax error while parsing %s\n" f; close_in c end let cross_implem = wrapper Parse.implementation tr_structure let cross_interf = wrapper Parse.interface tr_signature (*s cross-referencing lex and yacc description files *) let input_string_inside_file ic loc = seek_in ic loc.Lex_syntax.start_pos.pos_cnum; let len = loc.Lex_syntax.end_pos.pos_cnum - loc.Lex_syntax.start_pos.pos_cnum in let buf = Bytes.create len in try really_input ic buf 0 len; Bytes.to_string buf with End_of_file -> assert false let lexer_function_inside_file ic loc = seek_in ic loc.Lex_syntax.start_pos.pos_cnum; let left = ref (loc.Lex_syntax.end_pos.pos_cnum - loc.Lex_syntax.start_pos.pos_cnum) in fun buf len -> let m = input ic buf 0 (min !left len) in for i=0 to pred m do (*i Printf.eprintf "%c" (String.get buf i); i*) if Bytes.get buf i = '$' then Bytes.set buf i ' ' done; left := !left - m; m let cross_action_inside_file msg f m loc = reset_cross f loc.Lex_syntax.start_pos.pos_cnum; let c = open_in f in let lexbuf = Lexing.from_function (lexer_function_inside_file c loc) in try tr_structure (Parse.implementation lexbuf); close_in c with Syntaxerr.Error _ | Syntaxerr.Escape_error | Lexer.Error _ -> begin if not !quiet then begin eprintf "File \"%s\", character %d\n" f loc.Lex_syntax.start_pos.pos_cnum; eprintf " ** warning: syntax error while parsing %s\n" msg end; close_in c end let cross_type_inside_file f m loc = reset_cross f (loc.Lex_syntax.start_pos.pos_cnum - 7); let c = open_in f in let lexbuf = Lexing.from_string ("type t=" ^ input_string_inside_file c loc) in try tr_structure (Parse.implementation lexbuf); close_in c with Syntaxerr.Error _ | Syntaxerr.Escape_error | Lexer.Error _ -> begin if not !quiet then begin eprintf "File \"%s\", character %d\n" f loc.Lex_syntax.start_pos.pos_cnum; eprintf " ** warning: syntax error while parsing type\n" end; close_in c end let transl_loc loc = { loc_start = loc.Lex_syntax.start_pos; loc_end = loc.Lex_syntax.end_pos; loc_ghost = false } (*s cross-referencing lex description files *) let rec add_used_regexps f m r = match r with Lex_syntax.Ident (id,loc) -> add_uses (transl_loc loc) RegExpr id | Lex_syntax.Sequence(r1,r2) -> add_used_regexps f m r1; add_used_regexps f m r2 | Lex_syntax.Alternative(r1,r2) -> add_used_regexps f m r1; add_used_regexps f m r2 | Lex_syntax.Repetition(r) -> add_used_regexps f m r | Lex_syntax.Epsilon | Lex_syntax.Characters _ -> () let traverse_lex_defs f m lexdefs = (* Caution : header, actions and trailer must be traversed last, since traversing an action changes the location offset *) (* traverse named regexps *) List.iter (fun (id,loc,regexp) -> add_def (transl_loc loc) RegExpr id; add_used_regexps f m regexp) lexdefs.Lex_syntax.named_regexps; (* traverse lexer rules *) List.iter (fun (id,loc,rules) -> add_def (transl_loc loc) LexParseRule id; List.iter (fun (r,_) -> add_used_regexps f m r) rules) lexdefs.Lex_syntax.entrypoints; (* now we can traverse actions *) (* traverse header *) cross_action_inside_file "header" f m lexdefs.Lex_syntax.header; (* traverse actions *) List.iter (fun (id,loc,rules) -> List.iter (fun (regexp,action) -> add_used_regexps f m regexp; cross_action_inside_file "action" f m action) rules) lexdefs.Lex_syntax.entrypoints; (* traverse trailer *) cross_action_inside_file "trailer" f m lexdefs.Lex_syntax.trailer let cross_lex f m = reset_cross f 0; add_module m; let c = open_in f in let lexbuf = Lexing.from_channel c in try let lexdefs = Lex_parser.lexer_definition Lex_lexer.main lexbuf in traverse_lex_defs f m lexdefs; close_in c with Parsing.Parse_error | Lex_lexer.Lexical_error _ -> begin if not !quiet then eprintf " ** warning: syntax error while parsing lex file %s\n" f; close_in c end (*s cross-referencing yacc description files *) let traverse_yacc f m yacc_defs = (* Caution : header, actions and trailer must be traversed last, since traversing an action changes the location offset *) (* traverse decls *) let tokens = List.fold_left (fun acc decl -> match decl with | Yacc_syntax.Typed_tokens(typ,idl) -> List.fold_left (fun acc (id,loc) -> add_def (transl_loc loc) YaccTerminal id; Stringset.add id acc) acc idl | Yacc_syntax.Untyped_tokens(idl) -> List.fold_left (fun acc (id,loc) -> add_def (transl_loc loc) YaccTerminal id; Stringset.add id acc) acc idl | Yacc_syntax.Non_terminals_type(typ,idl) -> List.iter (fun (id,loc) -> add_uses (transl_loc loc) YaccNonTerminal id) idl; acc | Yacc_syntax.Start_symbols(idl) -> List.iter (fun (id,loc) -> add_uses (transl_loc loc) YaccNonTerminal id) idl; acc | Yacc_syntax.Tokens_assoc(idl) -> List.iter (fun (id,loc) -> add_uses (transl_loc loc) YaccTerminal id) idl; acc) Stringset.empty yacc_defs.Yacc_syntax.decls in (* traverse grammar rules *) List.iter (fun ((id,loc),rhss) -> add_def (transl_loc loc) YaccNonTerminal id; List.iter (fun (rhs,_) -> List.iter (fun (id,loc) -> if Stringset.mem id tokens then add_uses (transl_loc loc) YaccTerminal id else add_uses (transl_loc loc) YaccNonTerminal id) rhs) rhss) yacc_defs.Yacc_syntax.rules; (* now let's traverse types, actions, header, trailer *) (* traverse header *) cross_action_inside_file "header" f m yacc_defs.Yacc_syntax.header; (* traverse types in decls *) List.iter (function | Yacc_syntax.Typed_tokens(typ,idl) -> cross_type_inside_file f m typ | Yacc_syntax.Non_terminals_type(typ,idl) -> cross_type_inside_file f m typ | _ -> ()) yacc_defs.Yacc_syntax.decls; (* traverse actions *) List.iter (fun (_,rhss) -> List.iter (fun (_,action) -> cross_action_inside_file "action" f m action) rhss) yacc_defs.Yacc_syntax.rules; (* traverse trailer *) cross_action_inside_file "trailer" f m yacc_defs.Yacc_syntax.trailer let cross_yacc f m = reset_cross f 0; add_module m; let c = open_in f in let lexbuf = Lexing.from_channel c in try Yacc_lexer.reset_lexer f lexbuf; let yacc_defs = Yacc_parser.yacc_definitions Yacc_lexer.main lexbuf in traverse_yacc f m yacc_defs; close_in c with | Parsing.Parse_error -> begin Yacc_syntax.issue_warning "syntax error"; close_in c end | Yacc_lexer.Lexical_error(msg,line,col) -> begin Yacc_syntax.issue_warning ("lexical error (" ^ msg ^ ")"); close_in c end ocamlweb-1.41/cross.mli0000644000246300004300000000365713422556306014436 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*s That module exports to global tables [used] and [defined], indexed by identifiers (strings) and containing respectively the sets of locations where they are defined and used. Those locations are of type [where], which contain the name of the file and the absolute position in the source. *) type where = { w_filename : string; w_loc : int } type entry_type = | Value | Constructor | Field | Label | Type | Exception | Module | ModuleType | Class | Method | LexParseRule (*r CAMLLEX entry points *) | RegExpr (*r CAMLLEX regular expressions *) | YaccNonTerminal (*r CAMLYACC non-terminal symbols *) | YaccTerminal (*r CAMLYACC terminal symbols, i.e. tokens *) type index_entry = { e_name : string; e_type : entry_type } module Idmap : Map.S with type key = index_entry module Stringset : Set.S with type elt = string module Whereset : Set.S with type elt = where val used : Whereset.t Idmap.t ref val defined : Whereset.t Idmap.t ref (*s The two following functions fill the above tables for a given file. *) val cross_implem : string -> string -> unit val cross_interf : string -> string -> unit (* cross-referencing lex and yacc description files *) val cross_lex : string -> string -> unit val cross_yacc : string -> string -> unit ocamlweb-1.41/doclexer.mli0000644000246300004300000000301413422556306015075 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*s Caml files are represented by the record [caml_file], which contains their file names and their module names. The functions [module_name] and [make_caml_file] are used to construct such values. *) type caml_file = { caml_filename : string; caml_module : string } val module_name : string -> string val make_caml_file : string -> caml_file type file_type = | File_impl of caml_file | File_intf of caml_file | File_lex of caml_file | File_yacc of caml_file | File_other of string (*s The following function [read_one_file] reads a Caml file, separating the sections, and separating the paragraphs inside the sections. The boolean reference [skip_header] indicates whether the header must be skipped. [web_style] records if web sections were used anywhere in any file. *) val skip_header : bool ref val web_style : bool ref val read_one_file : file_type -> Web.file ocamlweb-1.41/doclexer.mll0000644000246300004300000005153213422556306015110 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) { open Printf open Lexing open Output open Web open Pretty (*s Global variables and functions used by the lexer. *) (* [skip_header] tells whether option \verb|--header| has been selected by the user. *) let skip_header = ref true (* for displaying error message if any, [current_file] records the name of the file currently read, and [comment_or_string_start] records the starting position of the comment or the string currently being read. *) let current_file = ref "" let comment_or_string_start = ref 0 (* [brace_depth] records the current depth of imbrication of braces \verb|{..}|, to know in lex files whether we are in an action or not. [lexyacc_brace_start] records the position of the starting brace of the current action, to display an error message if this brace is unclosed. *) let in_lexyacc_action = ref false let doublepercentcounter = ref 0 let brace_depth = ref 0 let lexyacc_brace_start = ref 0 (* [web_style] records if web sections were used anywhere in any file. *) let web_style = ref false (* global variables for temporarily recording data, for building the [Web.file] structure. *) let parbuf = Buffer.create 8192 let ignoring = ref false let push_char c = if not !ignoring then Buffer.add_char parbuf c let push_first_char lexbuf = if not !ignoring then Buffer.add_char parbuf (lexeme_char lexbuf 0) let push_string s = if not !ignoring then Buffer.add_string parbuf s let subparlist = ref ([] : sub_paragraph list) let push_caml_subpar () = if Buffer.length parbuf > 0 then begin subparlist := (CamlCode (Buffer.contents parbuf)) :: !subparlist; Buffer.clear parbuf end let push_lex_subpar () = if Buffer.length parbuf > 0 then begin subparlist := (LexCode (Buffer.contents parbuf)) :: !subparlist; Buffer.clear parbuf end let push_yacc_subpar () = if Buffer.length parbuf > 0 then begin subparlist := (YaccCode (Buffer.contents parbuf)) :: !subparlist; Buffer.clear parbuf end let parlist = ref ([] : paragraph list) let code_beg = ref 0 let push_code () = assert (List.length !subparlist = 0); if Buffer.length parbuf > 0 then begin parlist := (Code (!code_beg, Buffer.contents parbuf)) :: !parlist; Buffer.clear parbuf end let push_lexyacccode () = assert (Buffer.length parbuf = 0) ; if List.length !subparlist > 0 then begin parlist := (LexYaccCode (!code_beg, List.rev !subparlist)) :: !parlist; subparlist := [] end let big_section = ref false let initial_spaces = ref 0 let push_doc () = if Buffer.length parbuf > 0 then begin let doc = Documentation (!big_section, !initial_spaces, Buffer.contents parbuf) in parlist := doc :: !parlist; big_section := false; Buffer.clear parbuf end let push_latex () = if Buffer.length parbuf > 0 then begin let doc = RawLaTeX (Buffer.contents parbuf) in parlist := doc :: !parlist; big_section := false; Buffer.clear parbuf end let seclist = ref ([] : raw_section list) let section_beg = ref 0 let push_section () = if !parlist <> [] then begin let s = { sec_contents = List.rev !parlist; sec_beg = !section_beg } in seclist := s :: !seclist; parlist := [] end let reset_lexer f = current_file := f; comment_or_string_start := 0; section_beg := 0; code_beg := 0; parlist := []; seclist := []; in_lexyacc_action := false; doublepercentcounter := 0 let backtrack lexbuf = (*i eprintf "backtrack to %d\n" (lexbuf.lex_abs_pos + lexbuf.lex_start_pos); i*) lexbuf.lex_curr_pos <- lexbuf.lex_start_pos } (*s Shortcuts for regular expressions. *) let space = [' ' '\r' '\t'] let space_or_nl = [' ' '\t' '\r' '\n'] let character = "'" ( [^ '\\' '\''] | '\\' ['\\' '\'' 'n' 't' 'b' 'r'] | '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] ) "'" let up_to_end_of_comment = [^ '*']* '*' (([^ '*' ')'] [^ '*']* '*') | '*')* ')' (*s Entry point to skip the headers. Returns when headers are skipped. *) rule header = parse | "(*" { comment_or_string_start := lexeme_start lexbuf; skip_comment lexbuf; skip_spaces_until_nl lexbuf; header lexbuf } | "\n" { () } | space+ { header lexbuf } | _ { backtrack lexbuf } | eof { () } (* To skip a comment (used by [header]). *) and skip_comment = parse | "(*" { skip_comment lexbuf; skip_comment lexbuf } | "*)" { () } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocaml comment\n"; exit 1 } | _ { skip_comment lexbuf } (*s Same as [header] but for \textsf{OCamlYacc} *) and yacc_header = parse | "/*" { comment_or_string_start := lexeme_start lexbuf; skip_yacc_comment lexbuf; skip_spaces_until_nl lexbuf; yacc_header lexbuf } | "\n" { () } | space+ { yacc_header lexbuf } | _ { backtrack lexbuf } | eof { () } and skip_yacc_comment = parse | "/*" { skip_yacc_comment lexbuf; skip_yacc_comment lexbuf } | "*/" { () } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocamlyacc comment\n"; exit 1 } | _ { skip_yacc_comment lexbuf } (*s Recognizes a complete caml module body or interface, after header has been skipped. After calling that entry, the whole text read is in [seclist]. *) and caml_implementation = parse | _ { backtrack lexbuf; paragraph lexbuf; caml_implementation lexbuf } | eof { push_section () } (* recognizes a paragraph of caml code or documentation. After calling that entry, the paragraph has been added to [parlist]. *) and paragraph = parse | space* '\n' { paragraph lexbuf } | space* ";;" { paragraph lexbuf } | space* "(*" '*'* "*)" space* '\n' { paragraph lexbuf } | space* "(*" { comment_or_string_start := lexeme_start lexbuf; let s = lexeme lexbuf in initial_spaces := count_spaces (String.sub s 0 (String.length s - 2)); start_of_documentation lexbuf; push_doc () } | space* ("(*c" | _) { code_beg := lexeme_start lexbuf; backtrack lexbuf; caml_subparagraph lexbuf; push_code() } | eof { () } (* recognizes a whole lex description file, after header has been skipped. After calling that entry, the whole text read is in [seclist]. *) and lex_description = parse | _ { backtrack lexbuf; lex_paragraph lexbuf ; lex_description lexbuf } | eof { push_section () } and yacc_description = parse | _ { backtrack lexbuf ; yacc_paragraph lexbuf; yacc_description lexbuf } | eof { push_section () } (* Recognizes a paragraph of a lex description file. After calling that entry, the paragraph has been added to [parlist]. *) and lex_paragraph = parse | space* '\n' { lex_paragraph lexbuf } | space* "(*" '*'* "*)" space* '\n' { lex_paragraph lexbuf } | space* ("(*c" | _) { code_beg := lexeme_start lexbuf; backtrack lexbuf; lex_subparagraphs lexbuf ; push_lexyacccode() } | space* "(*" { comment_or_string_start := lexeme_start lexbuf; start_of_documentation lexbuf; push_doc () } | eof { () } and yacc_paragraph = parse | space* '\n' { yacc_paragraph lexbuf } | space* "/*" '*'* "*/" space* '\n' { if not !in_lexyacc_action then yacc_paragraph lexbuf else begin code_beg := lexeme_start lexbuf; backtrack lexbuf; yacc_subparagraphs lexbuf ; push_lexyacccode() end } | space* "/*" { if not !in_lexyacc_action then begin comment_or_string_start := lexeme_start lexbuf; start_of_yacc_documentation lexbuf; push_doc () end else begin code_beg := lexeme_start lexbuf; backtrack lexbuf; yacc_subparagraphs lexbuf ; push_lexyacccode() end } | space* "(*" '*'* "*)" space* '\n' { if !in_lexyacc_action then yacc_paragraph lexbuf else begin code_beg := lexeme_start lexbuf; backtrack lexbuf; yacc_subparagraphs lexbuf ; push_lexyacccode() end } | space* "(*" { if !in_lexyacc_action then begin comment_or_string_start := lexeme_start lexbuf; start_of_documentation lexbuf; push_doc () end else begin code_beg := lexeme_start lexbuf; backtrack lexbuf; yacc_subparagraphs lexbuf ; push_lexyacccode() end } | space* ("/*c" | "(*c" | _) { code_beg := lexeme_start lexbuf; backtrack lexbuf; yacc_subparagraphs lexbuf ; push_lexyacccode() } | eof { () } (*s At the beginning of the documentation part, just after the \verb|"(*"|. If the first character is ['s'], then a new section is started. After calling that entry, the [parbuf] buffer contains the doc read. *) (*i "*)" i*) and start_of_documentation = parse | space_or_nl+ { in_documentation lexbuf } | ('s' | 'S') space_or_nl* { web_style := true; push_section (); section_beg := lexeme_start lexbuf; big_section := (lexeme_char lexbuf 0 == 'S'); in_documentation lexbuf } | 'p' up_to_end_of_comment { let s = lexeme lexbuf in push_in_preamble (String.sub s 1 (String.length s - 3)) } | 'i' { ignore lexbuf } | 'l' { in_documentation lexbuf; push_latex () } | _ { backtrack lexbuf; in_documentation lexbuf } | eof { in_documentation lexbuf } and start_of_yacc_documentation = parse | space_or_nl+ { in_yacc_documentation lexbuf } | ('s' | 'S') space_or_nl* { web_style := true; push_section (); section_beg := lexeme_start lexbuf; big_section := (lexeme_char lexbuf 0 == 'S'); in_yacc_documentation lexbuf } | 'p' up_to_end_of_comment { let s = lexeme lexbuf in push_in_preamble (String.sub s 1 (String.length s - 3)) } | 'i' { yacc_ignore lexbuf } | 'l' { in_yacc_documentation lexbuf; push_latex () } | _ { backtrack lexbuf; in_yacc_documentation lexbuf } | eof { in_yacc_documentation lexbuf } (*s Inside the documentation part, anywhere after the "(*". After calling that entry, the [parbuf] buffer contains the doc read. *) (*i "*)" i*) and in_documentation = parse | "(*" { push_string "(*"; in_documentation lexbuf; push_string "*)"; in_documentation lexbuf } | "*)" { () } | '\n' " * " { push_char '\n'; in_documentation lexbuf } | '"' { push_char '"'; in_string lexbuf; in_documentation lexbuf } | character { push_string (lexeme lexbuf); in_documentation lexbuf } | _ { push_first_char lexbuf; in_documentation lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocaml comment\n"; exit 1 } (* yacc comments are NOT nested *) and in_yacc_documentation = parse | "*/" { () } | '\n' " * " { push_char '\n'; in_yacc_documentation lexbuf } | '"' { push_char '"'; in_string lexbuf; in_yacc_documentation lexbuf } | character { push_string (lexeme lexbuf); in_yacc_documentation lexbuf } | _ { push_first_char lexbuf; in_yacc_documentation lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocamlyacc comment\n"; exit 1 } (*s Recognizes a subparagraph of caml code. After calling that entry, the [parbuf] buffer contains the code read. *) and caml_subparagraph = parse | space* '\n' space* '\n' { backtrack lexbuf } | ";;" { backtrack lexbuf } | eof { () } | "(*" | "(*c" { comment_or_string_start := lexeme_start lexbuf; push_string "(*"; comment lexbuf; caml_subparagraph lexbuf } | "(*i" { comment_or_string_start := lexeme_start lexbuf; ignore lexbuf; caml_subparagraph lexbuf } | '"' { comment_or_string_start := lexeme_start lexbuf; push_char '"'; in_string lexbuf; caml_subparagraph lexbuf } | '{' { incr brace_depth; push_char '{'; caml_subparagraph lexbuf } | '}' { if !brace_depth = 0 then backtrack lexbuf else begin decr brace_depth; push_char '}'; caml_subparagraph lexbuf end } | "%}" { if !brace_depth = 0 then backtrack lexbuf else begin decr brace_depth; push_string "%}"; caml_subparagraph lexbuf end } | character { push_string (lexeme lexbuf); caml_subparagraph lexbuf } | _ { push_first_char lexbuf; caml_subparagraph lexbuf } (*s Recognizes a sequence of subparagraphs of lex description, including CAML actions. After calling that entry, the subparagraphs read are in [subparlist]. *) and lex_subparagraphs = parse | space* '\n' space* '\n' { backtrack lexbuf } | ";;" { () } | eof { if !in_lexyacc_action then begin eprintf "File \"%s\", character %d\n" !current_file !lexyacc_brace_start; eprintf "Unclosed brace\n" ; exit 1 end } | '}' { if !in_lexyacc_action then begin push_char '}'; in_lexyacc_action := false; lex_subparagraph lexbuf; push_lex_subpar(); lex_subparagraphs lexbuf end else begin eprintf "File \"%s\", character %d\n" !current_file (lexeme_start lexbuf); eprintf "Unexpected closing brace "; exit 1 end } | _ { backtrack lexbuf; if !in_lexyacc_action then begin caml_subparagraph lexbuf; push_caml_subpar() end else begin lex_subparagraph lexbuf; push_lex_subpar() end; lex_subparagraphs lexbuf } and yacc_subparagraphs = parse | space* '\n' space* '\n' { backtrack lexbuf } | "%%" { if !in_lexyacc_action then begin push_string "%%"; caml_subparagraph lexbuf; push_caml_subpar(); yacc_subparagraphs lexbuf end else begin push_yacc_subpar(); push_string "%%"; push_yacc_subpar(); incr doublepercentcounter; if !doublepercentcounter >= 2 then in_lexyacc_action := true end } | ";;" { if !in_lexyacc_action then () else begin push_string ";;"; yacc_subparagraph lexbuf; push_yacc_subpar(); yacc_subparagraphs lexbuf end } | eof { if !in_lexyacc_action && !doublepercentcounter <= 1 then begin eprintf "File \"%s\", character %d\n" !current_file !lexyacc_brace_start; eprintf "Unclosed brace\n" ; exit 1 end } | '}' { if !in_lexyacc_action then begin push_char '}'; in_lexyacc_action := false; yacc_subparagraph lexbuf; push_yacc_subpar(); yacc_subparagraphs lexbuf end else begin eprintf "File \"%s\", character %d\n" !current_file (lexeme_start lexbuf); eprintf "Unexpected closing brace "; exit 1 end } | "%}" { if !in_lexyacc_action then begin push_string "%}"; in_lexyacc_action := false; yacc_subparagraph lexbuf; push_yacc_subpar(); yacc_subparagraphs lexbuf end else begin eprintf "File \"%s\", character %d\n" !current_file (lexeme_start lexbuf); eprintf "Unexpected closing brace "; exit 1 end } | _ { backtrack lexbuf; if !in_lexyacc_action then begin caml_subparagraph lexbuf; push_caml_subpar() end else begin yacc_subparagraph lexbuf; push_yacc_subpar() end; yacc_subparagraphs lexbuf } (*s Recognizes a subparagraph of lex description. After calling that entry, the subparagraph read is in [parbuf]. *) and lex_subparagraph = parse | space* '\n' space* '\n' { backtrack lexbuf } | ";;" { backtrack lexbuf } | eof { () } | "(*" | "(*c" { comment_or_string_start := lexeme_start lexbuf; push_string "(*"; comment lexbuf; lex_subparagraph lexbuf } | space* "(*i" { comment_or_string_start := lexeme_start lexbuf; ignore lexbuf; lex_subparagraph lexbuf } | '"' { comment_or_string_start := lexeme_start lexbuf; push_char '"'; in_string lexbuf; lex_subparagraph lexbuf } | '{' { lexyacc_brace_start := lexeme_start lexbuf; push_char '{'; in_lexyacc_action := true } | character { push_string (lexeme lexbuf); lex_subparagraph lexbuf } | _ { push_first_char lexbuf; lex_subparagraph lexbuf } and yacc_subparagraph = parse | space* '\n' space* '\n' { backtrack lexbuf } | "%%" { backtrack lexbuf } | ";;" { backtrack lexbuf } | eof { () } | "/*" | "/*c" { comment_or_string_start := lexeme_start lexbuf; push_string "/*"; yacc_comment lexbuf; yacc_subparagraph lexbuf } | space* "/*i" { comment_or_string_start := lexeme_start lexbuf; yacc_ignore lexbuf; yacc_subparagraph lexbuf } | '"' { comment_or_string_start := lexeme_start lexbuf; push_char '"'; in_string lexbuf; yacc_subparagraph lexbuf } | "%{" { lexyacc_brace_start := lexeme_start lexbuf; push_string "%{"; in_lexyacc_action := true } | '{' { lexyacc_brace_start := lexeme_start lexbuf; push_char '{'; in_lexyacc_action := true } | '<' { lexyacc_brace_start := lexeme_start lexbuf; push_char '<'; push_yacc_subpar (); yacc_type lexbuf; yacc_subparagraph lexbuf } | character { push_string (lexeme lexbuf); yacc_subparagraph lexbuf } | _ { push_first_char lexbuf; yacc_subparagraph lexbuf } and yacc_type = parse | "->" { push_string "->"; yacc_type lexbuf } | '>' { push_caml_subpar(); push_char '>' } | _ { push_first_char lexbuf; yacc_type lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !lexyacc_brace_start; eprintf "Unclosed '<'"; exit 1 } (*s To skip spaces until a newline. *) and skip_spaces_until_nl = parse | space* '\n'? { () } | eof { () } | _ { backtrack lexbuf } (*s To read a comment inside a piece of code. *) and comment = parse | "(*" | "(*c" { push_string "(*"; comment lexbuf; comment lexbuf } | "*)" { push_string "*)" } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocaml comment\n"; exit 1 } | _ { push_first_char lexbuf; comment lexbuf } and yacc_comment = parse | "*/" { push_string "*/" } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocamlyacc comment\n"; exit 1 } | _ { push_first_char lexbuf; yacc_comment lexbuf } (*s Ignored parts, between "(*i" and "i*)". Note that such comments are not nested. *) and ignore = parse | "i*)" { skip_spaces_until_nl lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocamlweb comment\n"; exit 1 } | _ { ignore lexbuf } and yacc_ignore = parse | "i*/" { skip_spaces_until_nl lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocamlweb comment\n"; exit 1 } | _ { yacc_ignore lexbuf } (*s Strings in code. *) and in_string = parse | '"' { push_char '"' } | '\\' ['\\' '"' 'n' 't' 'b' 'r'] { push_string (lexeme lexbuf); in_string lexbuf } | eof { eprintf "File \"%s\", character %d\n" !current_file !comment_or_string_start; eprintf "Unterminated ocaml string\n"; exit 1 } | _ { push_first_char lexbuf; in_string lexbuf } { (*s \textbf{Caml files.} *) type caml_file = { caml_filename : string; caml_module : string } let module_name f = String.capitalize (Filename.basename f) let make_caml_file f = { caml_filename = f; caml_module = module_name (Filename.chop_extension f) } type file_type = | File_impl of caml_file | File_intf of caml_file | File_lex of caml_file | File_yacc of caml_file | File_other of string (*s \textbf{Reading Caml files.} *) let raw_read_file header entry f = reset_lexer f; let c = open_in f in let buf = Lexing.from_channel c in if !skip_header then header buf; entry buf; close_in c; List.rev !seclist let read header entry m = { content_file = m.caml_filename; content_name = m.caml_module; content_contents = raw_read_file header entry m.caml_filename; } let read_one_file = function | File_impl m -> Implem (read header caml_implementation m) | File_intf m -> Interf (read header caml_implementation m) | File_lex m -> Lex (read header lex_description m) | File_yacc m -> Yacc (read yacc_header yacc_description m) | File_other f -> Other f } ocamlweb-1.41/main.ml0000644000246300004300000003146213422556306014053 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i*) open Filename open Printf open Output open Web open Doclexer (*i*) (*s \textbf{Usage.} Printed on error output. *) let usage () = prerr_endline ""; prerr_endline "Usage: ocamlweb "; prerr_endline " -o write output into "; prerr_endline " --dvi output in DVI format (using latex)"; prerr_endline " --ps output in PostScript format (using dvips)"; prerr_endline " --pdf output in PDF format (using pdflatex)"; prerr_endline " --html output in HTML format (using hevea)"; prerr_endline " --hevea-option "; prerr_endline " pass an option to hevea (HTML output)"; prerr_endline " -s (short) no titles for files"; prerr_endline " --noweb use manual LaTeX sectioning, not WEB"; prerr_endline " --header do not skip the headers of Caml file"; prerr_endline " --no-preamble suppress LaTeX header and trailer"; prerr_endline " --no-index do not output the index"; prerr_endline " --extern-defs keep external definitions in the index"; prerr_endline " --impl consider as a .ml file"; prerr_endline " --intf consider as a .mli file"; prerr_endline " --tex consider as a .tex file"; prerr_endline " --latex-option "; prerr_endline " pass an option to the LaTeX package ocamlweb.sty"; prerr_endline " --class-options "; prerr_endline " set the document class options (default is `12pt')"; prerr_endline " --encoding set the character encoding (default is 'utf8')"; prerr_endline " --old-fullpage use LaTeX package fullpage with no option"; prerr_endline " -p insert something in LaTeX preamble"; prerr_endline " --files read file names to process in "; prerr_endline " --quiet quiet mode"; prerr_endline " --no-greek disable use of greek letters for type variables"; prerr_endline ""; prerr_endline "On-line documentation at http://www.lri.fr/~filliatr/ocamlweb/\n"; exit 1 (*s \textbf{License informations.} Printed when using option \verb!--warranty!. *) let copying () = prerr_endline " This program is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License version 2, as published by the Free Software Foundation. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License version 2 for more details (enclosed in the file LGPL)."; flush stderr (*s \textbf{Banner.} Always printed. Notice that it is printed on error output, so that when the output of \ocamlweb\ is redirected this header is not (unless both standard and error outputs are redirected, of course). *) let banner () = eprintf "This is ocamlweb version %s, compiled on %s\n" Version.version Version.date; eprintf "Copyright (c) 1999-2000 Jean-Christophe Filliâtre and Claude Marché\n"; eprintf "This is free software with ABSOLUTELY NO WARRANTY (use option -warranty)\n"; flush stderr (*s \textbf{Separation of files.} Files given on the command line are separated according to their type, which is determined by their suffix. Implementations and interfaces have respective suffixes \verb!.ml! and \verb!.mli! and \LaTeX\ files have suffix \verb!.tex!. *) let check_if_file_exists f = if not (Sys.file_exists f) then begin eprintf "\nocamlweb: %s: no such file\n" f; exit 1 end let what_file f = check_if_file_exists f; if check_suffix f ".ml" then File_impl (make_caml_file f) else if check_suffix f ".mli" then File_intf (make_caml_file f) else if check_suffix f ".mll" then File_lex (make_caml_file f) else if check_suffix f ".mly" then File_yacc (make_caml_file f) else if check_suffix f ".tex" then File_other f else begin eprintf "\nocamlweb: don't know what to do with %s\n" f; exit 1 end (*s \textbf{Reading file names from a file.} File names may be given in a file instead of being given on the command line. [(files_from_file f)] returns the list of file names contained in the file named [f]. These file names must be separated by spaces, tabulations or newlines. *) let files_from_file f = let files_from_channel ch = let buf = Buffer.create 80 in let l = ref [] in try while true do match input_char ch with | ' ' | '\t' | '\n' -> if Buffer.length buf > 0 then l := (Buffer.contents buf) :: !l; Buffer.clear buf | c -> Buffer.add_char buf c done; [] with End_of_file -> List.rev !l in try check_if_file_exists f; let ch = open_in f in let l = files_from_channel ch in close_in ch;l with Sys_error s -> begin eprintf "\nocamlweb: cannot read from file %s (%s)\n" f s; exit 1 end (*s \textbf{Parsing of the command line.} Output file, if specified, is kept in [output_file]. *) let output_file = ref "" let dvi = ref false let ps = ref false let pdf = ref false let html = ref false let hevea_options = ref ([] : string list) let parse () = let files = ref [] in let add_file f = files := f :: !files in let rec parse_rec = function | [] -> () | ("-header" | "--header") :: rem -> skip_header := false; parse_rec rem | ("-noweb" | "--noweb" | "-no-web" | "--no-web") :: rem -> web := false; parse_rec rem | ("-web" | "--web") :: rem -> web := true; parse_rec rem | ("-nopreamble" | "--nopreamble" | "--no-preamble") :: rem -> set_no_preamble true; parse_rec rem | ("-p" | "--preamble") :: s :: rem -> push_in_preamble s; parse_rec rem | ("-p" | "--preamble") :: [] -> usage () | ("-noindex" | "--noindex" | "--no-index") :: rem -> index := false; parse_rec rem | ("-o" | "--output") :: f :: rem -> output_file := f; parse_rec rem | ("-o" | "--output") :: [] -> usage () | ("-s" | "--short") :: rem -> short := true; parse_rec rem | ("-dvi" | "--dvi") :: rem -> dvi := true; parse_rec rem | ("-ps" | "--ps") :: rem -> ps := true; parse_rec rem | ("-pdf" | "--pdf") :: rem -> pdf := true; parse_rec rem | ("-html" | "--html") :: rem -> html := true; parse_rec rem | ("-hevea-option" | "--hevea-option") :: [] -> usage () | ("-hevea-option" | "--hevea-option") :: s :: rem -> hevea_options := s :: !hevea_options; parse_rec rem | ("-extern-defs" | "--extern-defs") :: rem -> extern_defs := true; parse_rec rem | ("-q" | "-quiet" | "--quiet") :: rem -> quiet := true; parse_rec rem | ("--nogreek" | "--no-greek") :: rem -> use_greek_letters := false; parse_rec rem | ("-h" | "-help" | "-?" | "--help") :: rem -> banner (); usage () | ("-v" | "-version" | "--version") :: _ -> banner (); exit 0 | ("-warranty" | "--warranty") :: _ -> copying (); exit 0 | "--class-options" :: s :: rem -> class_options := s; parse_rec rem | "--class-options" :: [] -> usage () | "--latex-option" :: s :: rem -> add_latex_option s; parse_rec rem | "--latex-option" :: [] -> usage () | "--encoding" :: s :: rem -> encoding := s; parse_rec rem | "--encoding" :: [] -> usage () | "--old-fullpage" :: rem -> fullpage_headings := false; parse_rec rem | ("-impl" | "--impl") :: f :: rem -> check_if_file_exists f; let n = if Filename.check_suffix f ".mll" || Filename.check_suffix f ".mly" then Filename.chop_extension f else f in let m = File_impl { caml_filename = f; caml_module = module_name n } in add_file m; parse_rec rem | ("-impl" | "--impl") :: [] -> usage () | ("-intf" | "--intf") :: f :: rem -> check_if_file_exists f; let i = File_intf { caml_filename = f; caml_module = module_name f } in add_file i; parse_rec rem | ("-intf" | "--intf") :: [] -> usage () | ("-tex" | "--tex") :: f :: rem -> add_file (File_other f); parse_rec rem | ("-tex" | "--tex") :: [] -> usage () | ("-files" | "--files") :: f :: rem -> List.iter (fun f -> add_file (what_file f)) (files_from_file f); parse_rec rem | ("-files" | "--files") :: [] -> usage () | f :: rem -> add_file (what_file f); parse_rec rem in parse_rec (List.tl (Array.to_list Sys.argv)); List.rev !files (*s The following function produces the output. The default output is the \LaTeX\ document: in that case, we just call [Web.produce_document]. If option \verb!-dvi!, \verb!-ps!, \verb!-pdf!, or \verb!-html! is invoked, then we make calls to \verb!latex!, \verb!dvips!, \verb!pdflatex!, and/or \verb!hevea! accordingly. *) let locally dir f x = let cwd = Sys.getcwd () in try Sys.chdir dir; let y = f x in Sys.chdir cwd; y with e -> Sys.chdir cwd; raise e let clean_temp_files basefile = let remove f = try Sys.remove f with _ -> () in remove (basefile ^ ".tex"); remove (basefile ^ ".log"); remove (basefile ^ ".aux"); remove (basefile ^ ".dvi"); remove (basefile ^ ".ps"); remove (basefile ^ ".haux"); remove (basefile ^ ".html") let clean_and_exit basefile res = clean_temp_files basefile; exit res let cat file = let c = open_in file in try while true do print_char (input_char c) done with End_of_file -> close_in c let copy src dst = let cin = open_in src and cout = open_out dst in try while true do Pervasives.output_char cout (input_char cin) done with End_of_file -> close_in cin; close_out cout let produce_output fl = if not (!dvi || !ps || !pdf || !html) then begin if !output_file <> "" then set_output_to_file !output_file; produce_document fl end else begin let texfile = temp_file "ocamlweb" ".tex" in let basefile = chop_suffix texfile ".tex" in set_output_to_file texfile; produce_document fl; let latex = if !pdf then "pdflatex" else "latex" in let command = let file = basename texfile in let file = if !quiet then sprintf "'\\nonstopmode\\input{%s}'" file else file in sprintf "(%s %s && %s %s) 1>&2 %s" latex file latex file (if !quiet then "> /dev/null" else "") in let res = locally (dirname texfile) Sys.command command in if res <> 0 then begin eprintf "Couldn't run LaTeX successfully\n"; clean_and_exit basefile res end; let dvifile = basefile ^ ".dvi" in if !dvi then begin if !output_file <> "" then (* we cannot use Sys.rename accross file systems *) copy dvifile !output_file else cat dvifile end; if !ps then begin let psfile = if !output_file <> "" then !output_file else basefile ^ ".ps" in let command = sprintf "dvips %s -o %s %s" dvifile psfile (if !quiet then "> /dev/null 2>&1" else "") in let res = Sys.command command in if res <> 0 then begin eprintf "Couldn't run dvips successfully\n"; clean_and_exit basefile res end; if !output_file = "" then cat psfile end; if !pdf then begin let pdffile = basefile ^ ".pdf" in if !output_file <> "" then (* we cannot use Sys.rename accross file systems *) copy pdffile !output_file else cat pdffile end; if !html then begin let htmlfile = if !output_file <> "" then !output_file else basefile ^ ".html" in let options = String.concat " " (List.rev !hevea_options) in let command = sprintf "hevea %s ocamlweb.sty %s -o %s %s" options texfile htmlfile (if !quiet then "> /dev/null 2>&1" else "") in let res = Sys.command command in if res <> 0 then begin eprintf "Couldn't run hevea successfully\n"; clean_and_exit basefile res end; if !output_file = "" then cat htmlfile end; clean_temp_files basefile end (*s \textbf{Main program.} Print the banner, parse the command line, read the files and then call [produce_document] from module [Web]. *) let main () = let files = parse() in if List.length files > 0 then begin let l = List.map read_one_file files in if !web_style then begin if not !web && not !quiet then begin eprintf "Warning: web sections encountered while in noweb style, ignored.\n"; flush stderr end end else web := false; if not !web then add_latex_option "noweb"; produce_output l end let _ = Printexc.catch main () ocamlweb-1.41/output.ml0000644000246300004300000004221613422556306014466 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*i*) open Printf (*i*) (*s \textbf{Low level output.} [out_channel] is a reference on the current output channel. It is initialized to the standard output and can be redirect to a file by the function [set_output_to_file]. The function [close_output] closes the output channel if it is a file. [output_char], [output_string] and [output_file] are self-explainable. *) let out_channel = ref stdout let output_is_file = ref false let set_output_to_file f = out_channel := open_out f; output_is_file := true let close_output () = if !output_is_file then close_out !out_channel let quiet = ref false let short = ref false let output_char c = Pervasives.output_char !out_channel c let output_string s = Pervasives.output_string !out_channel s let output_file f = let ch = open_in f in try while true do Pervasives.output_char !out_channel (input_char ch) done with End_of_file -> close_in ch (*s \textbf{High level output.} In this section and the following, we introduce functions which are \LaTeX\ dependent. *) (*s [output_verbatim] outputs a string in verbatim mode. A valid delimiter is given by the function [char_out_of_string]. It assumes that one of the four characters of [fresh_chars] is not used (which is the case in practice, since [output_verbatim] is only used to print quote-delimited characters). *) let fresh_chars = [ '!'; '|'; '"'; '+' ] let char_out_of_string s = let rec search = function | [] -> assert false | c :: r -> if String.contains s c then search r else c in search fresh_chars let output_verbatim s = let c = char_out_of_string s in output_string (sprintf "\\verb%c%s%c" c s c) let no_preamble = ref false let set_no_preamble b = no_preamble := b let (preamble : string Queue.t) = Queue.create () let push_in_preamble s = Queue.add s preamble let class_options = ref "12pt" let fullpage_headings = ref true let encoding = ref "utf8" let latex_header opt = if not !no_preamble then begin output_string (sprintf "\\documentclass[%s]{article}\n" !class_options); output_string (sprintf "\\usepackage[%s]{inputenc}\n" !encoding); (*i output_string "\\usepackage[T1]{fontenc}\n"; i*) if !fullpage_headings then output_string "\\usepackage[headings]{fullpage}\n" else output_string "\\usepackage{fullpage}\n"; output_string "\\usepackage"; if opt <> "" then output_string (sprintf "[%s]" opt); output_string "{ocamlweb}\n"; output_string "\\pagestyle{headings}\n"; Queue.iter (fun s -> output_string s; output_string "\n") preamble; output_string "\\begin{document}\n" end; output_string "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"; output_string "%% This file has been automatically generated with the command\n"; output_string "%% "; Array.iter (fun s -> output_string s; output_string " ") Sys.argv; output_string "\n"; output_string "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n" let latex_trailer () = if not !no_preamble then begin output_string "\\end{document}\n" end (*s \textbf{Math mode.} We keep a boolean, [math_mode], to know if we are currently already in \TeX\ math mode. The functions [enter_math] and [leave_math] inserts \verb!$! if necessary, and switch that boolean. *) let math_mode = ref false let enter_math () = if not !math_mode then begin output_string "$"; math_mode := true end let leave_math () = if !math_mode then begin output_string "$"; math_mode := false end (*s \textbf{Indentation.} An indentation at the beginning of a line of $n$ spaces is produced by [(indentation n)] (used for code only). *) let indentation n = let space = 0.5 *. (float n) in output_string (sprintf "\\ocwindent{%2.2fem}\n" space) (*s \textbf{End of lines.} [(end_line ())] ends a line. (used for code only). *) let end_line () = leave_math (); output_string "\\ocweol\n" let end_line_string () = output_string "\\endgraf\n" (*s \textbf{Keywords.} Caml keywords and base type are stored in two hash tables, and the two functions [is_caml_keyword] and [is_base_type] make the corresponding tests. The function [output_keyword] prints a keyword, with different macros for base types and keywords. *) let build_table l = let h = Hashtbl.create 101 in List.iter (fun key -> Hashtbl.add h key ()) l; Hashtbl.mem h let is_caml_keyword = build_table [ "and"; "as"; "assert"; "begin"; "class"; "constraint"; "do"; "done"; "downto"; "else"; "end"; "exception"; "external"; "false"; "for"; "fun"; "function"; "functor"; "if"; "in"; "include"; "inherit"; "initializer"; "lazy"; "let"; "match"; "method"; "module"; "mutable"; "new"; "object"; "of"; "open"; "or"; "parser"; "private"; "rec"; "sig"; "struct"; "then"; "to"; "true"; "try"; "type"; "val"; "virtual"; "when"; "while"; "with"; "mod"; "land"; "lor"; "lxor"; "lsl"; "lsr"; "asr" ] let is_base_type = build_table [ "string"; "int"; "array"; "unit"; "bool"; "char"; "list"; "option"; "float"; "ref" ] let is_lex_keyword = build_table [ "rule"; "let"; "and"; "parse"; "eof"; "as" ] let is_yacc_keyword = build_table [ "%token"; "%left"; "%right"; "%type"; "%start"; "%nonassoc"; "%prec"; "error" ] let is_keyword s = is_base_type s || is_caml_keyword s let output_keyword s = if is_base_type s then output_string "\\ocwbt{" else output_string "\\ocwkw{"; output_string s; output_string "}" let output_lex_keyword s = output_string "\\ocwlexkw{"; output_string s; output_string "}" let output_yacc_keyword s = output_string "\\ocwyacckw{"; if String.get s 0 = '%' then output_string "\\"; output_string s; output_string "}" (*s \textbf{Identifiers.} The function [output_raw_ident] prints an identifier, escaping the \TeX\ reserved characters with [output_escaped_char]. The function [output_ident] prints an identifier, calling [output_keyword] if necessary. *) let output_escaped_char c = if c = '^' || c = '~' then leave_math(); match c with | '\\' -> output_string "\\symbol{92}" | '$' | '#' | '%' | '&' | '{' | '}' | '_' -> output_char '\\'; output_char c | '^' | '~' -> output_char '\\'; output_char c; output_string "{}" | '<' | '>' -> output_string "\\ensuremath{"; output_char c; output_string "}" | _ -> output_char c let output_latex_id s = for i = 0 to String.length s - 1 do output_escaped_char s.[i] done type char_type = Upper | Lower | Symbol let what_char = function | 'A'..'Z' | '\192'..'\214' | '\216'..'\222' -> Upper | 'a'..'z' |'\223'..'\246' | '\248'..'\255' | '_' -> Lower | _ -> Symbol let what_is_first_char s = if String.length s > 0 then what_char s.[0] else Lower let output_raw_ident_in_index s = begin match what_is_first_char s with | Upper -> output_string "\\ocwupperid{" | Lower -> output_string "\\ocwlowerid{" | Symbol -> output_string "\\ocwsymbolid{" end; output_latex_id s; output_string "}" let output_raw_ident s = begin match what_is_first_char s with | Upper -> output_string "\\ocwupperid{" | Lower -> output_string "\\ocwlowerid{" | Symbol -> output_string "\\ocwsymbolid{" end; try let qualification = Filename.chop_extension s in (* We extract the qualified name. *) let qualified_name = String.sub s (String.length qualification + 1) (String.length s - String.length qualification - 1) in (* We check now whether the qualified term is a lower id or not. *) match qualified_name.[0] with | 'A'..'Z' -> (* The qualified term is a module or a constructor: nothing to change. *) output_latex_id (s); output_string "}" | _ -> (* The qualified term is a value or a type: \verb!\\ocwlowerid! used instead. *) output_latex_id (qualification ^ "."); output_string "}"; output_string "\\ocwlowerid{"; output_latex_id qualified_name; output_string "}" with Invalid_argument _ -> (* The string [s] is a module name or a constructor: nothing to do. *) output_latex_id s; output_string "}" let output_ident s = if is_keyword s then begin leave_math (); output_keyword s end else begin enter_math (); output_raw_ident s end let output_lex_ident s = if is_lex_keyword s then begin leave_math (); output_lex_keyword s end else begin enter_math (); output_string "\\ocwlexident{"; output_latex_id s; output_string "}"; end let output_yacc_ident s = if is_yacc_keyword s then begin leave_math (); output_yacc_keyword s end else begin enter_math (); output_string "\\ocwyaccident{"; output_latex_id s; output_string "}"; end (*s \textbf{Symbols.} Some mathematical symbols are printed in a nice way, in order to get a more readable code. The type variables from \verb!'a! to \verb!'d! are printed as Greek letters for the same reason. *) let output_symbol = function | "*" -> enter_math (); output_string "\\times{}" | "**" -> enter_math (); output_string "*\\!*" | "->" -> enter_math (); output_string "\\rightarrow{}" | "<-" -> enter_math (); output_string "\\leftarrow{}" | "<=" -> enter_math (); output_string "\\le{}" | ">=" -> enter_math (); output_string "\\ge{}" | "<>" -> enter_math (); output_string "\\not=" | "==" -> enter_math (); output_string "\\equiv" | "!=" -> enter_math (); output_string "\\not\\equiv" | "~-" -> enter_math (); output_string "-" | "[<" -> enter_math (); output_string "[\\langle{}" | ">]" -> enter_math (); output_string "\\rangle{}]" | "<" | ">" | "(" | ")" | "[" | "]" | "[|" | "|]" as s -> enter_math (); output_string s | "&" | "&&" -> enter_math (); output_string "\\land{}" | "or" | "||" -> enter_math (); output_string "\\lor{}" | "not" -> enter_math (); output_string "\\lnot{}" | "[]" -> enter_math (); output_string "[\\,]" | "|" -> enter_math (); output_string "\\mid{}" | s -> output_latex_id s let use_greek_letters = ref true let output_tv id = output_string "\\ocwtv{"; output_latex_id id; output_char '}' let output_greek l = enter_math (); output_char '\\'; output_string l; output_string "{}" let output_type_variable id = if not !use_greek_letters then output_tv id else match id with | "a" -> output_greek "alpha" | "b" -> output_greek "beta" | "c" -> output_greek "gamma" | "d" -> output_greek "delta" | "e" -> output_greek "varepsilon" | "i" -> output_greek "iota" | "k" -> output_greek "kappa" | "l" -> output_greek "lambda" | "m" -> output_greek "mu" | "n" -> output_greek "nu" | "r" -> output_greek "rho" | "s" -> output_greek "sigma" | "t" -> output_greek "tau" | _ -> output_tv id let output_ascii_char n = output_string (sprintf "\\symbol{%d}" n) (*s \textbf{Constants.} *) let output_integer s = let n = String.length s in let base b = let v = String.sub s 2 (n - 2) in output_string (sprintf "\\ocw%sconst{%s}" b v) in if n > 1 then match s.[1] with | 'x' | 'X' -> base "hex" | 'o' | 'O' -> base "oct" | 'b' | 'B' -> base "bin" | _ -> output_string s else output_string s let output_float s = try let i = try String.index s 'e' with Not_found -> String.index s 'E' in let m = String.sub s 0 i in let e = String.sub s (succ i) (String.length s - i - 1) in if m = "1" then output_string (sprintf "\\ocwfloatconstexp{%s}" e) else output_string (sprintf "\\ocwfloatconst{%s}{%s}" m e) with Not_found -> output_string s (*s \textbf{Comments.} *) let output_bc () = leave_math (); output_string "\\ocwbc{}" let output_ec () = leave_math (); output_string "\\ocwec{}" let output_hfill () = leave_math (); output_string "\\hfill " let output_byc () = leave_math (); output_string "\\ocwbyc{}" let output_eyc () = leave_math (); output_string "\\ocweyc{}" (*s \textbf{Strings.} *) let output_bs () = leave_math (); output_string "\\ocwstring{\"" let output_es () = output_string "\"}" let output_vspace () = output_string "\\ocwvspace{}" (*s Reset of the output machine. *) let reset_output () = math_mode := false (*s \textbf{Sectioning commands.} *) let begin_section () = output_string "\\allowbreak\\ocwsection\n" let output_typeout_command filename = output_string "\\typeout{OcamlWeb file "; output_string filename; output_string "}\n" let output_module module_name = if not !short then begin output_typeout_command (module_name^".ml"); output_string "\\ocwmodule{"; output_latex_id module_name; output_string "}\n" end let output_interface module_name = if not !short then begin output_typeout_command (module_name^".mli"); output_string "\\ocwinterface{"; output_latex_id module_name; output_string "}\n" end let output_lexmodule module_name = if not !short then begin output_typeout_command (module_name^".mll"); output_string "\\ocwlexmodule{"; output_latex_id module_name; output_string "}\n" end let output_yaccmodule module_name = if not !short then begin output_typeout_command (module_name^".mly"); output_string "\\ocwyaccmodule{"; output_latex_id module_name; output_string "}\n" end let in_code = ref false let begin_code () = if not !in_code then output_string "\\ocwbegincode{}"; in_code := true let end_code () = if !in_code then output_string "\\ocwendcode{}"; in_code := false let begin_dcode () = output_string "\\ocwbegindcode{}" let end_dcode () = output_string "\\ocwenddcode{}" let last_is_code = ref false let begin_code_paragraph () = if not !last_is_code then output_string "\\medskip\n"; last_is_code := true let end_code_paragraph is_last_paragraph = if is_last_paragraph then end_line() else output_string "\\medskip\n\n" let begin_doc_paragraph is_first_paragraph n = if not is_first_paragraph then indentation n; last_is_code := false let end_doc_paragraph () = output_string "\n" (*s \textbf{Index.} It is opened and closed with the two macros \verb!ocwbeginindex! and \verb!ocwendindex!. The auxiliary function [print_list] is a generic function to print a list with a given printing function and a given separator. *) let begin_index () = output_string "\n\n\\ocwbeginindex{}\n" let end_index () = output_string "\n\n\\ocwendindex{}\n" let print_list print sep l = let rec print_rec = function | [] -> () | [x] -> print x | x::r -> print x; sep(); print_rec r in print_rec l (*s \textbf{Index in WEB style.} The function [output_index_entry] prints one entry line, given the name of the entry, and two lists of pre-formatted sections labels, like 1--4,7,10--17, of type [string elem list]. The first list if printed in bold face (places where the identifier is defined) and the second one in roman (places where it is used). *) type 'a elem = Single of 'a | Interval of 'a * 'a let output_ref r = output_string (sprintf "\\ref{%s}" r) let output_elem = function | Single r -> output_ref r | Interval (r1,r2) -> output_ref r1; output_string "--"; output_ref r2 let output_bf_elem n = output_string "\\textbf{"; output_elem n; output_string "}" let output_index_entry s t def use = let sep () = output_string ", " in output_string "\\ocwwebindexentry{"; enter_math (); output_raw_ident_in_index s; leave_math (); if t <> "" then output_string (" " ^ t); output_string "}{"; print_list output_bf_elem sep def; output_string "}{"; if def <> [] && use <> [] then output_string ", "; print_list output_elem sep use; output_string "}\n" (*s \textbf{Index in \LaTeX\ style.} When we are not in WEB style, the index in left to \LaTeX, and all the work is done by the macro \verb!\ocwrefindexentry!, which takes three arguments: the name of the entry and the two lists of labels where it is defined and used, respectively. *) let output_raw_index_entry s t def use = let sep () = output_string "," and sep' () = output_string ", " in output_string "\\ocwrefindexentry{"; enter_math (); output_raw_ident_in_index s; leave_math (); if t <> "" then output_string (" " ^ t); output_string "}{"; print_list output_string sep def; output_string "}{"; print_list output_string sep use; output_string "}{"; print_list output_ref sep' def; output_string "}{"; print_list output_ref sep' use; output_string "}\n" let output_label l = output_string "\\label{"; output_string l; output_string "}%\n" ocamlweb-1.41/output.mli0000644000246300004300000001372713422556306014644 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*s In that module, we concentrate all the printing functions. Thus, it will be easy to add another kind of output, HTML for instance, by adapting the code of that module, and nothing else. Default output is to standard output, but it can be redirected to a file with [set_output_to_file]. [close_output] closes the output, if it is a file. *) val set_output_to_file : string -> unit val close_output : unit -> unit (*s These mutable flags controls the output. If [quiet], no extra output is done on standard output, default is [false]. If [use_greek_letters] is true, greek letters are used to display (some of) the single-letter type variables, default is [true]. *) val quiet : bool ref val use_greek_letters : bool ref val short : bool ref (*s Then we introduce some low level output functions, for characters and strings. [(output_file f)] copies the contents of file [f] on the output. [(output_verbatim s)] outputs the string [s] `as is'. *) val output_char : char -> unit val output_string : string -> unit val output_file : string -> unit val output_verbatim : string -> unit (*s The following functions are mainly useful for a \LaTeX\ output, but will work correctly in other cases. A call to [set_no_preamble] suppresses the output of the header and trailer. [(end_line ())] ends a line, [(indentation n)] introduces an indentation of size [n] at the beggining of a line. [latex_header] takes as argument the options of the \LaTeX\ package ocamlweb.sty. *) val class_options : string ref val encoding: string ref val set_no_preamble : bool -> unit val push_in_preamble : string -> unit val fullpage_headings : bool ref val latex_header : string -> unit val latex_trailer : unit -> unit val indentation : int -> unit val end_line : unit -> unit val end_line_string : unit -> unit val enter_math : unit -> unit val leave_math : unit -> unit (*s The following functions are used to pretty-print the code. [is_keyword] identifies the keywords of Objective Caml. [output_ident] outputs an identifier, in different faces for keywords and other identifiers, escaping the characters that need it, like \_ for instance in \LaTeX. [output_escaped_char] pretty-prints the reserved char of \LaTeX, like \verb!&! or \verb!$!. [output_symbol] pretty-prints the Caml symbols, like $\rightarrow$ for \texttt{->}. [output_type_variable s] pretty-prints type variables, in particular one-letter type variables are output as greek letters. [output_ascii_char n] outputs the character of ASCII code [n]. *) type char_type = Upper | Lower | Symbol val what_is_first_char : string -> char_type val is_keyword : string -> bool val output_ident : string -> unit val output_escaped_char : char -> unit val output_symbol : string -> unit val output_type_variable : string -> unit val output_ascii_char : int -> unit (* [output_lex_ident] (resp. [output_yacc_ident]) outputs an identifier as above but taking into account CAMLLEX keywords (resp. CAMLYACC keywords) *) val output_lex_ident : string -> unit val output_yacc_ident : string -> unit (*s Constants are typeset by the following functions. *) val output_integer : string -> unit val output_float : string -> unit (*s Comments inside code are opened and closed respectively by [output_bc] and [output_ec]. The function [output_hfill] is called before [output_bc] to justify a comment. [output_byc] and [output_eyc] are the same for CAMLYACC comments, that is \verb|/*|\ldots\verb|*/|. *) val output_bc : unit -> unit val output_ec : unit -> unit val output_byc : unit -> unit val output_eyc : unit -> unit val output_hfill : unit -> unit (*s Strings inside code are opened and close respectively by [ output_bs] and [output_es]. A space character in a string is output as a visible space, with [output_vspace]. *) val output_bs : unit -> unit val output_es : unit -> unit val output_vspace : unit -> unit (*s The following functions deal with sectioning. The highest level is the one of modules and interfaces. The next level is the one of section. The last level is the one of paragraphs, which are atomic pieces of documentation or code. *) val output_module : string -> unit val output_interface : string -> unit val output_lexmodule : string -> unit val output_yaccmodule : string -> unit val begin_section : unit -> unit val begin_code : unit -> unit val end_code : unit -> unit val begin_dcode : unit -> unit val end_dcode : unit -> unit val begin_code_paragraph : unit -> unit val end_code_paragraph : bool -> unit val begin_doc_paragraph : bool -> int -> unit val end_doc_paragraph : unit -> unit (*s Index functions. [(output_index_entry id t def use)] outputs an entry line for identifier [id], with type [t], where [def] is the list of sections where [f] is introduced and [use] the list of sections where [f] is used. If the type of the entry is [""], then it is omitted. *) type 'a elem = Single of 'a | Interval of 'a * 'a val begin_index : unit -> unit val output_index_entry : string -> string -> string elem list -> string elem list -> unit val output_raw_index_entry : string -> string -> string list -> string list -> unit val end_index : unit -> unit val output_label : string -> unit (*s The parameters of the output engine are reset to their initial values with [reset_output]. *) val reset_output : unit -> unit ocamlweb-1.41/pretty.mli0000644000246300004300000000261713422556306014627 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*s The following functions pretty-print the paragraphs of code and documentation, respectively. The boolean argument indicates whether the given paragraph is the last one for [pretty_print_code] or the first one for [pretty_print_doc]. *) val pretty_print_code : bool -> string -> unit val pretty_print_doc : bool -> bool * int * string -> unit (*s These three functions pretty-print subparagraphs of Caml code, Camllex code and Camlyacc code respectively *) val pretty_print_caml_subpar : string -> unit val pretty_print_lex_subpar : string -> unit val pretty_print_yacc_subpar : string -> unit (*s This function sets values in order to reset the lexer, so we could call it on an another file. *) val reset_pretty : unit -> unit val count_spaces : string -> int ocamlweb-1.41/pretty.mll0000644000246300004300000003233213422556306014627 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) { open Printf open Output open Lexing (*s Global variables and functions used by the lexer. *) (* [comment_depth] indicates how many opening-braces we saw, so we know how many closing-braces we have to look for, in order to respect caml's-specifications concerning comments imbrication. *) let comment_depth = ref 0 (* Accounts for braket-depth in order to imbricate them. *) let bracket_depth = ref 0 (* Set a reference on the starting character when we see [\verb]. *) let verb_delim = ref (Char.chr 0) (* counts occurences of "%%" in yacc files *) let yaccdoublepercentcounter = ref 0 (* This function returns the first char of a lexbuf. *) let first_char lexbuf = lexeme_char lexbuf 0 (* The [count_spaces] function acccounts for spaces in order to respect alignment (in the \LaTeX{}-outputed file) concerning left margins. *) let count_spaces s = let c = ref 0 in for i = 0 to String.length s - 1 do if s.[i] = '\t' then c := !c + (8 - (!c mod 8)) else incr c done; !c (* This boolean value is true if we enter in math mode, false otherwise. *) let user_math_mode = ref false (* [user_math] function does everything is needed to set the math mode when it is called, particularly it checks/sets the [user_math_mode] value as needed. *) let user_math () = if not !user_math_mode then begin user_math_mode := true; enter_math () end else begin user_math_mode := false; leave_math () end (* Checks if we are in maths mode and prints char c considering the case. *) let check_user_math c = if !user_math_mode then output_char c else output_escaped_char c (* This function sets values in order to reset the lexer, so we could call it on an another file. *) let reset_pretty () = reset_output (); yaccdoublepercentcounter := 0; user_math_mode := false } (*s Shortcuts for regular expressions. *) let space = [' ' '\t'] let lowercase = ['a'-'z' '\223'-'\246' '\248'-'\255' '_'] let uppercase = ['A'-'Z' '\192'-'\214' '\216'-'\222'] (* This is for the identifiers as specified in caml's specifications. *) let identchar = ['A'-'Z' 'a'-'z' '_' '\192'-'\214' '\216'-'\246' '\248'-'\255' '\'' '0'-'9'] let identifier = (lowercase | uppercase) identchar* (* This one helps protecting special caracters. *) let symbolchar = ['!' '$' '%' '&' '*' '+' '-' '.' '/' ':' '<' '=' '>' '?' '@' '^' '|' '~'] let caml_token = "[" | "]" | "[|" | "|]" | "[<" | ">]" | "{" | "}" | "{<" | ">}" | "[]" | "(" | ")" | "or" | "not" | "||" let symbol_token = caml_token | (symbolchar+) let character = "'" ( [^ '\\' '\''] | '\\' ['\\' '\'' 'n' 't' 'b' 'r'] | '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] ) "'" let decimal_literal = ['0'-'9']+ let hex_literal = '0' ['x' 'X'] ['0'-'9' 'A'-'F' 'a'-'f']+ let oct_literal = '0' ['o' 'O'] ['0'-'7']+ let bin_literal = '0' ['b' 'B'] ['0'-'1']+ let float_literal = ['0'-'9']+ ('.' ['0'-'9']*)? (['e' 'E'] ['+' '-']? ['0'-'9']+)? (*s Pretty-printing of code. Main entry points for Caml and Lex and Yacc files, counts for spaces in order to respect alignment. The following function pretty-prints some code and assumes that we are at the beginning of a line. *) rule pr_camlcode = parse | space* { let n = count_spaces (lexeme lexbuf) in indentation n; pr_camlcode_inside lexbuf; pr_camlcode lexbuf } | eof { leave_math () } and pr_lexcode = parse | space* { let n = count_spaces (lexeme lexbuf) in indentation n; pr_lexcode_inside lexbuf; pr_lexcode lexbuf } | eof { leave_math () } and pr_yacccode = parse | space* { let n = count_spaces (lexeme lexbuf) in indentation n; pr_yacccode_inside lexbuf; pr_yacccode lexbuf } | eof { leave_math () } (*s That function pretty-prints the Caml code anywhere else. *) and pr_camlcode_inside = parse | '\n' { end_line () } | space+ { output_char '~'; pr_camlcode_inside lexbuf } | character { output_verbatim (lexeme lexbuf); pr_camlcode_inside lexbuf } | "'" identifier { let id = lexeme lexbuf in output_type_variable (String.sub id 1 (pred (String.length id))); pr_camlcode_inside lexbuf } | "(*r" { output_hfill (); output_bc (); comment_depth := 1; pr_comment lexbuf; pr_camlcode_inside lexbuf } | "(*" { output_bc (); comment_depth := 1; pr_comment lexbuf; pr_camlcode_inside lexbuf } | '"' { output_bs (); pr_code_string lexbuf; pr_camlcode_inside lexbuf } | symbol_token { output_symbol (lexeme lexbuf); pr_camlcode_inside lexbuf } | (identifier '.')* identifier { output_ident (lexeme lexbuf); pr_camlcode_inside lexbuf } | eof { () (*i end_line() supprime par dorland-muller i*) } | decimal_literal | hex_literal | oct_literal | bin_literal { output_integer (lexeme lexbuf); pr_camlcode_inside lexbuf } | float_literal { output_float (lexeme lexbuf); pr_camlcode_inside lexbuf } | _ { output_escaped_char (first_char lexbuf); pr_camlcode_inside lexbuf } (*s That function pretty-prints the Lex code anywhere else. *) and pr_lexcode_inside = parse | '_' { output_string "\\ocwlexwc"; pr_lexcode_inside lexbuf } | '*' { enter_math (); output_string "^\\star{}"; pr_lexcode_inside lexbuf } | '+' { enter_math (); output_string "^{\\scriptscriptstyle +}"; pr_lexcode_inside lexbuf } | '-' { leave_math (); output_string "--"; pr_lexcode_inside lexbuf } | '|' { enter_math (); output_string "\\mid{}"; pr_lexcode_inside lexbuf } | '\n' { end_line () } | space+ { output_char '~'; pr_lexcode_inside lexbuf } | character { output_verbatim (lexeme lexbuf); pr_lexcode_inside lexbuf } | "(*" { output_bc (); comment_depth := 1; pr_comment lexbuf; pr_lexcode_inside lexbuf } | "(*r" { output_hfill (); output_bc (); comment_depth := 1; pr_comment lexbuf; pr_lexcode_inside lexbuf } | '"' { output_bs (); pr_code_string lexbuf; pr_lexcode_inside lexbuf } | identifier { output_lex_ident (lexeme lexbuf); pr_lexcode_inside lexbuf } | eof { () } | _ { output_escaped_char (first_char lexbuf); pr_lexcode_inside lexbuf } (*s That function pretty-prints the Yacc code anywhere else. *) and pr_yacccode_inside = parse | "%%" { incr yaccdoublepercentcounter; output_string (if !yaccdoublepercentcounter = 1 then "\\ocwyaccrules" else "\\ocwyacctrailer"); pr_yacccode_inside lexbuf } | "%{" { output_string "\\ocwyaccopercentbrace"; pr_yacccode_inside lexbuf } | "%}" { output_string "\\ocwyacccpercentbrace"; pr_yacccode_inside lexbuf } | ":" { output_string "\\ocwyacccolon"; pr_yacccode_inside lexbuf } | ";" { output_string "\\ocwyaccendrule"; pr_yacccode_inside lexbuf } | "|" { output_string "\\ocwyaccpipe"; pr_yacccode_inside lexbuf } | '\n' { end_line (); } | space+ { output_char '~'; pr_yacccode_inside lexbuf } | "/*r" { output_hfill (); output_byc (); pr_yacc_comment lexbuf; pr_yacccode_inside lexbuf } | "/*" { output_byc (); pr_yacc_comment lexbuf; pr_yacccode_inside lexbuf } | '%'? identifier { output_yacc_ident (lexeme lexbuf); pr_yacccode_inside lexbuf } | _ { output_escaped_char (first_char lexbuf); pr_yacccode_inside lexbuf } | eof { () } (*s Comments. *) and pr_comment = parse | "(*" { output_bc (); incr comment_depth; pr_comment lexbuf } | "*)" { output_ec (); decr comment_depth; if !comment_depth > 0 then pr_comment lexbuf } (*i utile ????? | '\n' space* '*' ' ' { output_string "\n "; pr_comment lexbuf } i*) | '"' { output_bs (); pr_code_string lexbuf; pr_comment lexbuf; } | '[' { if !user_math_mode then output_char '[' else begin bracket_depth := 1; begin_dcode (); escaped_code lexbuf; end_dcode () end; pr_comment lexbuf } | eof { () } | "\\$" { output_string (lexeme lexbuf); pr_comment lexbuf } | '$' { user_math(); pr_comment lexbuf } | _ { output_char (first_char lexbuf); pr_comment lexbuf } (* The [C_like_comments] are not inbricable *) and pr_yacc_comment = parse | "*/" { output_eyc (); } | '\n' space* '*' ' ' { output_string "\n "; pr_yacc_comment lexbuf } | '[' { if !user_math_mode then output_char '[' else begin bracket_depth := 1; begin_dcode (); escaped_code lexbuf; end_dcode () end; pr_yacc_comment lexbuf } | eof { () } | "\\$" { output_string (lexeme lexbuf); pr_yacc_comment lexbuf } | '$' { user_math(); pr_yacc_comment lexbuf } | _ { output_char (first_char lexbuf); pr_yacc_comment lexbuf } (*s Strings in code. *) and pr_code_string = parse | '"' { output_es () } | '\n' { end_line_string (); pr_code_string lexbuf } | ' ' { output_vspace (); pr_code_string lexbuf } | '\\' ['"' 't' 'b' 'r'] { output_escaped_char '\\'; output_char (lexeme_char lexbuf 1); pr_code_string lexbuf } | '\\' '\n' { output_escaped_char '\\'; end_line_string (); pr_code_string lexbuf } | '\\' '\\' { output_escaped_char '\\'; output_escaped_char '\\'; pr_code_string lexbuf } | eof { () } | '-' { output_ascii_char 45; pr_code_string lexbuf } | _ { output_escaped_char (first_char lexbuf); pr_code_string lexbuf } (*s Escaped code. *) and escaped_code = parse | '[' { output_char '['; incr bracket_depth; escaped_code lexbuf } | ']' { decr bracket_depth; if !bracket_depth > 0 then begin output_char ']'; escaped_code lexbuf end else if not !user_math_mode then leave_math () } | '"' { output_bs (); pr_code_string lexbuf; escaped_code lexbuf } | space+ { output_char '~'; escaped_code lexbuf } | character { output_verbatim (lexeme lexbuf); escaped_code lexbuf } | "'" identifier { let id = lexeme lexbuf in output_type_variable (String.sub id 1 (pred (String.length id))); escaped_code lexbuf } | symbol_token { output_symbol (lexeme lexbuf); escaped_code lexbuf } | identifier { output_ident (lexeme lexbuf); escaped_code lexbuf } | eof { if not !user_math_mode then leave_math () } | decimal_literal | hex_literal | oct_literal | bin_literal { output_integer (lexeme lexbuf); escaped_code lexbuf } | float_literal { output_float (lexeme lexbuf); escaped_code lexbuf } | _ { output_escaped_char (first_char lexbuf); escaped_code lexbuf } (*s Documentation. It is output `as is', except for quotations. *) and pr_doc = parse | '[' { if !user_math_mode then output_char '[' else begin bracket_depth := 1; begin_dcode (); escaped_code lexbuf; end_dcode () end; pr_doc lexbuf } | "\\$" { output_string (lexeme lexbuf); pr_doc lexbuf } | '$' { user_math(); pr_doc lexbuf } | "\\verb" _ { verb_delim := lexeme_char lexbuf 5; output_string (lexeme lexbuf); pr_verb lexbuf; pr_doc lexbuf } | "\\begin{verbatim}" { output_string (lexeme lexbuf); pr_verbatim lexbuf; pr_doc lexbuf } | eof { () } | _ { output_char (first_char lexbuf); pr_doc lexbuf } and pr_doc_title = parse | '[' { if !user_math_mode then output_char '[' else begin bracket_depth := 1; begin_dcode (); escaped_code lexbuf; end_dcode () end; pr_doc_title lexbuf } | '.' { output_string ".}\\quad{}" } | eof { () } | _ { output_char (first_char lexbuf); pr_doc_title lexbuf } and pr_verb = parse | eof { () } | _ { let c = lexeme_char lexbuf 0 in output_char c; if c == !verb_delim then () else pr_verb lexbuf } and pr_verbatim = parse | "\\end{verbatim}" { output_string (lexeme lexbuf) } | eof { () } | _ { output_char (lexeme_char lexbuf 0); pr_verbatim lexbuf } { (*s pretty-printing subparagraphs *) let pretty_print_caml_subpar s = pr_camlcode (Lexing.from_string s) let pretty_print_lex_subpar s = pr_lexcode (Lexing.from_string s) let pretty_print_yacc_subpar s = pr_yacccode (Lexing.from_string s) (*s Then we can introduce two functions [pretty_print_code] and [pretty_print_doc], which pretty-print respectively code and documentation parts. *) let pretty_print_code is_last_paragraph s = pr_camlcode (Lexing.from_string s); end_code_paragraph is_last_paragraph let pretty_print_doc is_first_paragraph (big,n,s) = begin_doc_paragraph is_first_paragraph n; let lb = Lexing.from_string s in if big then begin output_string "\\textbf{"; pr_doc_title lb end; pr_doc lb; end_doc_paragraph () } ocamlweb-1.41/web.ml0000644000246300004300000003030713422556306013701 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (*i*) open Filename open Cross open Output open Pretty (*i*) type sub_paragraph = | CamlCode of string | LexCode of string | YaccCode of string type paragraph = | Documentation of bool * int * string | RawLaTeX of string | Code of int * string | LexYaccCode of int * (sub_paragraph list) type raw_section = { sec_contents : paragraph list; sec_beg : int } type content = { content_file : string; content_name : string; content_contents : raw_section list } type file = | Implem of content | Interf of content | Lex of content | Yacc of content | Other of string (*i To print a "Web.file" (for testing) *) let print_string s = Format.printf "\"%s\"" s (* To print c "(" arg with the function pr ")" *) let print c pr arg = Format.printf "@[%s(@," c; pr arg; Format.printf ")@]" (* to print a list between "[" "]" *) let rec print_end_list f = function | [] -> Format.printf "]@]" | x :: l -> Format.printf ";@ "; f x; print_end_list f l let print_list f = function | [] -> Format.printf "[]" | x :: l -> Format.printf "@[[ "; f x; print_end_list f l (* To print a subparagraph *) let print_sub_paragraph = function | CamlCode s -> print "CamlCode" print_string s; | LexCode s -> print "LexCode" print_string s; | YaccCode s -> print "YaccCode" print_string s (* To print a paragraph *) let print_paragraph = function | Documentation (_,_,s) -> print "Documentation" print_string s | RawLaTeX (s) -> print "RawLaTeX" print_string s | Code (i,s) -> Format.printf "Code(%d,@ %s)" i s | LexYaccCode (i,spl) -> Format.printf "@[LexYaccCode(%d,@ " i; print_list print_sub_paragraph spl; Format.printf ")@]" (* To print a section *) let print_raw_section { sec_contents = sc; sec_beg = sb } = Format.printf "@[{ sec_beg = %d ;@ sec_contents =@ " sb ; print_list print_paragraph sc; Format.printf ";@ }@]" (* To print a [Web.content] *) let print_content { content_file = c; content_name = cn; content_contents = rl } = Format.printf "@[{ content_file = \"%s\" ;@ content_name = \"%s\" ;@ contents_contents =@ " c cn ; print_list print_raw_section rl ; Format.printf ";@ }@]" (* To print a [Web.file] *) let print_file f = begin match f with | Implem c -> print "Implem" print_content c | Interf c -> print "Interf" print_content c | Lex c -> print "Lex" print_content c | Yacc c -> print "Yacc" print_content c | Other s -> print "Other" print_string s end; Format.printf "@." (*i*) (*s Options of the engine. *) let index = ref true let web = ref true let extern_defs = ref false let latex_options = ref "" let add_latex_option s = if !latex_options = "" then latex_options := s else latex_options := !latex_options ^ "," ^ s (*s Construction of the global index. *) let index_file = function | Implem i -> cross_implem i.content_file i.content_name | Interf i -> cross_interf i.content_file i.content_name | Yacc i -> cross_yacc i.content_file i.content_name | Lex i -> cross_lex i.content_file i.content_name | Other _ -> () let build_index l = List.iter index_file l (*s The locations tables. \label{counters} *) module Smap = Map.Make(struct type t = string let compare = compare end) let sec_locations = ref Smap.empty let code_locations = ref Smap.empty let add_loc table file ((_,s) as loc) = let l = try Smap.find file !table with Not_found -> [(0,s)] in table := Smap.add file (loc :: l) !table let add_par_loc = let par_counter = ref 0 in fun f p -> match p with | Code (l,_) -> incr par_counter; add_loc code_locations f (l,!par_counter) | LexYaccCode (l,_) -> incr par_counter; add_loc code_locations f (l,!par_counter) | Documentation _ -> () | RawLaTeX _ -> () let add_sec_loc = let sec_counter = ref 0 in fun f s -> incr sec_counter; add_loc sec_locations f (s.sec_beg,!sec_counter); (*i Printf.eprintf "section %d starts at character %d of file %s\n" !sec_counter s.sec_beg f; i*) List.iter (add_par_loc f) s.sec_contents let add_file_loc it = List.iter (add_sec_loc it.content_file) it.content_contents let locations_for_a_file = function | Implem i -> add_file_loc i | Interf i -> add_file_loc i | Lex i -> add_file_loc i | Yacc i -> add_file_loc i | Other _ -> () let find_where w = let rec lookup = function | [] -> raise Not_found | (l,n) :: r -> if w.w_loc >= l then ((w.w_filename,l),n) else lookup r in let table = if !web then !sec_locations else !code_locations in lookup (Smap.find w.w_filename table) (*s Printing of the index. *) (*s Alphabetic order for index entries. To sort index entries, we define the following order relation [alpha_string]. It puts symbols first (identifiers that do not begin with a letter), and symbols are compared using Caml's generic order relation. For real identifiers, we first normalize them by translating lowercase characters to uppercase ones and by removing all the accents, and then we use Caml's comparison. *) let norm_char c = match Char.uppercase c with | '\192'..'\198' -> 'A' | '\199' -> 'C' | '\200'..'\203' -> 'E' | '\204'..'\207' -> 'I' | '\209' -> 'N' | '\210'..'\214' | '\216' -> 'O' | '\217'..'\220' -> 'U' | '\221' -> 'Y' | c -> c let norm_string s = let u = Bytes.of_string s in for i = 0 to String.length s - 1 do Bytes.set u i (norm_char s.[i]) done; Bytes.to_string u let alpha_string s1 s2 = match what_is_first_char s1, what_is_first_char s2 with | Symbol, Symbol -> s1 < s2 | Symbol, _ -> true | _, Symbol -> false | _,_ -> norm_string s1 < norm_string s2 let order_entry e1 e2 = (alpha_string e1.e_name e2.e_name) || (e1.e_name = e2.e_name && e1.e_type < e2.e_type) (*s The following function collects all the index entries and sort them using [alpha_string], returning a list. *) module Idset = Set.Make(struct type t = index_entry let compare = compare end) let all_entries () = let s = Idmap.fold (fun x _ s -> Idset.add x s) !used Idset.empty in let s = Idmap.fold (fun x _ s -> Idset.add x s) !defined s in Sort.list order_entry (Idset.elements s) (*s When we are in \LaTeX\ style, an index entry only consists in two lists of labels, which are treated by the \LaTeX\ macro \verb!\ocwrefindexentry!. When we are in WEB style, we can do a bit better, replacing a list like 1,2,3,4,7,8,10 by 1--4,7,8,10, as in usual \LaTeX\ indexes. The following function [intervals] is used to group together the lists of at least three consecutive integers. *) let intervals l = let rec group = function | (acc, []) -> List.rev acc | (Interval (s1,(_,n2)) :: acc, (f,n) :: rem) when n = succ n2 -> group (Interval (s1,(f,n)) :: acc, rem) | ((Single _)::(Single (f1,n1))::acc, (f,n)::rem) when n = n1 + 2 -> group (Interval ((f1,n1),(f,n)) :: acc, rem) | (acc, (f,n) :: rem) -> group ((Single (f,n)) :: acc, rem) in group ([],l) let make_label_name (f,n) = f ^ ":" ^ (string_of_int n) let label_list l = List.map (fun x -> make_label_name (fst x)) l let elem_map f = function | Single x -> Single (f x) | Interval (x,y) -> Interval (f x, f y) let web_list l = let l = intervals l in List.map (elem_map (fun x -> make_label_name (fst x))) l (*s Printing one index entry. The function call [(list_in_table id t)] collects all the sections for the identifier [id] in the table [t], using the function [find_where], and sort the result thanks to the counter which was associated to each new location (see section~\ref{counters}). It also removes the duplicates labels. *) let rec uniquize = function | [] | [_] as l -> l | x :: (y :: r as l) -> if x = y then uniquize l else x :: (uniquize l) let map_succeed_nf f l = let rec map = function | [] -> [] | x :: l -> try (f x) :: (map l) with Not_found -> map l in map l let list_in_table id t = try let l = Whereset.elements (Idmap.find id t) in let l = map_succeed_nf find_where l in let l = Sort.list (fun x x' -> snd x < snd x') l in uniquize l with Not_found -> [] let entry_type_name = function | Value | Constructor -> "" | Field -> "(field)" | Label -> "(label)" | Type -> "(type)" | Exception -> "(exn)" | Module -> "(module)" | ModuleType -> "(sig)" | Class -> "(class)" | Method -> "(method)" | LexParseRule -> "(camllex parsing rule)" | RegExpr -> "(camllex regexpr)" | YaccNonTerminal -> "(camlyacc non-terminal)" | YaccTerminal -> "(camlyacc token)" let print_one_entry id = let def = list_in_table id !defined in if !extern_defs || def <> [] then begin let use = list_in_table id !used in let s = id.e_name in let t = entry_type_name id.e_type in if !web then output_index_entry s t (web_list def) (web_list use) else output_raw_index_entry s t (label_list def) (label_list use) end (*s Then printing the index is just iterating [print_one_entry] on all the index entries, given by [(all_entries())]. *) let print_index () = begin_index (); List.iter print_one_entry (all_entries()); end_index () (*s Pretty-printing of the document. *) let rec pretty_print_sub_paragraph = function | CamlCode(s) -> pretty_print_caml_subpar s | YaccCode(s) -> pretty_print_yacc_subpar s | LexCode(s) -> pretty_print_lex_subpar s let pretty_print_paragraph is_first_paragraph is_last_paragraph f = function | Documentation (b,n,s) -> end_code (); pretty_print_doc is_first_paragraph (b,n,s); end_line() (*i ajout Dorland-Muller i*) | RawLaTeX s -> end_code (); output_string s; end_line() | Code (l,s) -> if l > 0 then output_label (make_label_name (f,l)); begin_code_paragraph (); begin_code (); pretty_print_code is_last_paragraph s | LexYaccCode (l,s) -> if l > 0 then output_label (make_label_name (f,l)); begin_code_paragraph (); begin_code (); List.iter pretty_print_sub_paragraph s; end_code_paragraph is_last_paragraph let pretty_print_section first f s = if !web then begin_section (); if first && s.sec_beg > 0 then output_label (make_label_name (f,0)); output_label (make_label_name (f,s.sec_beg)); let rec loop is_first_paragraph = function | [] -> () | [ p ] -> pretty_print_paragraph is_first_paragraph true f p | p :: rest -> pretty_print_paragraph is_first_paragraph false f p; loop false rest in loop true s.sec_contents; end_code () let pretty_print_sections f = function | [] -> () | s :: r -> pretty_print_section true f s; List.iter (pretty_print_section false f) r let pretty_print_content output_header content = reset_pretty(); output_header content.content_name; pretty_print_sections content.content_file content.content_contents let pretty_print_file = function | Implem i -> pretty_print_content output_module i | Interf i -> pretty_print_content output_interface i | Lex i -> pretty_print_content output_lexmodule i | Yacc i -> pretty_print_content output_yaccmodule i | Other f -> output_file f (*s Production of the document. We proceed in three steps: \begin{enumerate} \item Build the index; \item Pretty-print of files; \item Printing of the index. \end{enumerate} *) let produce_document l = (*i List.iter print_file l; i*) List.iter locations_for_a_file l; build_index l; latex_header !latex_options; List.iter pretty_print_file l; if !index then print_index (); latex_trailer (); close_output () ocamlweb-1.41/web.mli0000644000246300004300000000577613422556306014066 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) (* This module is the heart of the program. The only function is [produce_document], which takes a list of files and produces the final \LaTeX\ document. *) (*s Source file structure. *) (* A source file is splitted into paragraphs of code and documentation. A new paragraph begins either when switching between code and comment or, within code, when an empty line occurs. A paragraph of documentation contains arbitrary text. A paragraph of CAML code is arbitrary CAML source text. A paragraph of LEX/YACC code is again a sequence of subparagraphs, which are either CAML source (actions), CAMLLEX syntax or CAMLYACC syntax *) type sub_paragraph = | CamlCode of string | LexCode of string | YaccCode of string type paragraph = | Documentation of bool * int * string | RawLaTeX of string | Code of int * string | LexYaccCode of int * (sub_paragraph list) (* A web section is a numbered part of a source file, which contains a sequence of paragraphs. The [sec_beg] field is the character position of the beginning of the web section inside the whole file *) type raw_section = { sec_contents : paragraph list; sec_beg : int } (* Finally, the contents of a source file is a sequence of web sections. The [content_file] field is the whole file name (including dirname and extension) whereas the [content_name] field is the corresponding module name *) type content = { content_file : string; content_name : string; content_contents : raw_section list } (*s A source file is either an implementation, an interface, a camllex description, a camlyacc description, or any other file, which is then considered as a \LaTeX\ file. *) type file = | Implem of content | Interf of content | Lex of content | Yacc of content | Other of string (*s Options. [index] indicates whether the index is to be produced; default value is [true]. [extern_defs] indicates whether identifiers used but not defined should appear in the index; default value is [false]. [web] indicates WEB style or not; default value is [true]. [add_latex_option] passed an option to the \texttt{ocamlweb} \LaTeX\ package. *) val extern_defs : bool ref val add_latex_option : string -> unit val index : bool ref val web : bool ref (*s Main entry: production of the document from a list of files. *) val produce_document : file list -> unit ocamlweb-1.41/yacc_lexer.mll0000644000246300004300000001716613422556306015426 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (*i $Id$ i*) { open Lex_syntax open Yacc_syntax open Yacc_parser (* Auxiliaries for the lexical analyzer *) let brace_depth = ref 0 and comment_depth = ref 0 and mark_count = ref 0 exception Lexical_error of string * int * int let handle_lexical_error fn lexbuf = let line = !current_line_num and column = Lexing.lexeme_start lexbuf - !current_line_start_pos in try fn lexbuf with Lexical_error(msg, _, _) -> raise(Lexical_error(msg, line, column)) (*s yacc keywords *) let keyword_table = Hashtbl.create 17 let _ = List.iter (fun (kwd, tok) -> Hashtbl.add keyword_table kwd tok) [ "token", Ttoken; "start", Tstart; "type", Ttype; "left", Tleft; "right", Tright; "nonassoc", Tnonassoc; "prec", Tprec ] let keyword_token lexbuf = try Hashtbl.find keyword_table (Lexing.lexeme lexbuf) with Not_found -> raise(Lexical_error ("unknown keyword " ^ String.escaped(Lexing.lexeme lexbuf), !current_line_num, Lexing.lexeme_start lexbuf - !current_line_start_pos)) let cur_loc lexbuf = { start_pos = Lexing.lexeme_start_p lexbuf; end_pos = Lexing.lexeme_end_p lexbuf; start_line = !current_line_num; start_col = Lexing.lexeme_start lexbuf - !current_line_start_pos } let reset_lexer f lexbuf = current_file_name := f; mark_count := 0; current_line_num := 1; current_line_start_pos := 0; current_lexbuf := lexbuf } (*s main rule for tokens in yacc files *) rule main = parse | [' ' '\013' '\009' '\012' ] + { main lexbuf } (* Although few grammar files include commas anywhere commas are skipped in yacc. The original yacc code is used for ocaml. See \verb|yacc/reader.c:nextc(),read_grammar()| from the ocaml 3.04 distribution. We issue a warning for non conformity to ocamlyacc documentation. *) | ',' { issue_warning "use of commas in mly files is allowed but not conform to ocamlyacc documentation"; main lexbuf } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; main lexbuf } | "/*" { handle_lexical_error yacc_comment lexbuf; main lexbuf } | ['A'-'Z' 'a'-'z'] ['A'-'Z' 'a'-'z' '\'' '_' '0'-'9'] * { match Lexing.lexeme lexbuf with "error" -> Terror | s -> let l = cur_loc lexbuf in (*i Printf.eprintf "ident '%s' occurs at (%d,%d)\n" s l.start_pos l.end_pos; i*) Tident (s,l) } | '{' { let n1 = Lexing.lexeme_end_p lexbuf and l1 = !current_line_num and s1 = !current_line_start_pos in brace_depth := 1; let n2 = handle_lexical_error action lexbuf in Taction({start_pos = n1; end_pos = n2; start_line = l1; start_col = n1.Lexing.pos_cnum - s1}) } | '|' { Tor } | ';' { Tsemicolon } | ':' { Tcolon } | '%' { yacc_keyword lexbuf } | '<' { let n1 = Lexing.lexeme_end_p lexbuf and l1 = !current_line_num and s1 = !current_line_start_pos in let n2 = handle_lexical_error typedecl lexbuf in Ttypedecl({start_pos = n1; end_pos = n2; start_line = l1; start_col = n1.Lexing.pos_cnum - s1}) } | eof { EOF } | _ { raise(Lexical_error ("illegal character " ^ String.escaped(Lexing.lexeme lexbuf), !current_line_num, Lexing.lexeme_start lexbuf - !current_line_start_pos)) } and yacc_keyword = parse | '%' { incr mark_count; if !mark_count = 1 then Tmark else let n1 = Lexing.lexeme_end_p lexbuf and l1 = !current_line_num and s1 = !current_line_start_pos in brace_depth := 0; let n2 = handle_lexical_error action lexbuf in Taction({start_pos = n1; end_pos = n2; start_line = l1; start_col = n1.Lexing.pos_cnum - s1}) } | '{' { let n1 = Lexing.lexeme_end_p lexbuf and l1 = !current_line_num and s1 = !current_line_start_pos in brace_depth := 1; let n2 = handle_lexical_error action lexbuf in Taction({start_pos = n1; end_pos = n2; start_line = l1; start_col = n1.Lexing.pos_cnum - s1}) } | ['a'-'z']+ { keyword_token lexbuf } | _ { raise(Lexical_error ("illegal character " ^ String.escaped(Lexing.lexeme lexbuf), !current_line_num, Lexing.lexeme_start lexbuf - !current_line_start_pos)) } (*s recognizes a CAML action *) and action = parse | '{' { incr brace_depth; action lexbuf } | '}' { decr brace_depth; if !brace_depth = 0 then Lexing.lexeme_start_p lexbuf else action lexbuf } | "%}" { decr brace_depth; if !brace_depth = 0 then Lexing.lexeme_start_p lexbuf else raise(Lexical_error ("ill-balanced brace ", !current_line_num, Lexing.lexeme_start lexbuf - !current_line_start_pos)) } | '"' { string lexbuf; action lexbuf } | "'" [^ '\\'] "'" { action lexbuf } | "'" '\\' ['\\' '\'' 'n' 't' 'b' 'r'] "'" { action lexbuf } | "'" '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { action lexbuf } | "(*" { comment_depth := 1; comment lexbuf; action lexbuf } | eof { if !brace_depth = 0 then Lexing.lexeme_start_p lexbuf else raise (Lexical_error("unterminated action", 0, 0)) } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; action lexbuf } | _ { action lexbuf } (*s recognizes a CAML type between $<$ and $>$ *) and typedecl = parse | '>' { Lexing.lexeme_start_p lexbuf } | eof { raise (Lexical_error("unterminated type declaration", 0, 0)) } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; typedecl lexbuf } | "->" { typedecl lexbuf } | _ { typedecl lexbuf } and string = parse '"' { () } | '\\' [' ' '\013' '\009' '\012'] * '\010' [' ' '\013' '\009' '\012'] * { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; string lexbuf } | '\\' ['\\' '"' 'n' 't' 'b' 'r'] { string lexbuf } | '\\' ['0'-'9'] ['0'-'9'] ['0'-'9'] { string lexbuf } | eof { raise(Lexical_error("unterminated string", 0, 0)) } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; string lexbuf } | _ { string lexbuf } and comment = parse "(*" { incr comment_depth; comment lexbuf } | "*)" { decr comment_depth; if !comment_depth = 0 then () else comment lexbuf } | '"' { string lexbuf; comment lexbuf } | "''" { comment lexbuf } | "'" [^ '\\' '\''] "'" { comment lexbuf } | "'\\" ['\\' '\'' 'n' 't' 'b' 'r'] "'" { comment lexbuf } | "'\\" ['0'-'9'] ['0'-'9'] ['0'-'9'] "'" { comment lexbuf } | eof { raise(Lexical_error("unterminated comment", 0, 0)) } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; comment lexbuf } | _ { comment lexbuf } and yacc_comment = parse | "*/" { () } | eof { raise(Lexical_error("unterminated yacc comment", 0, 0)) } | '\010' { current_line_start_pos := Lexing.lexeme_end lexbuf; incr current_line_num; yacc_comment lexbuf } | _ { yacc_comment lexbuf } ocamlweb-1.41/yacc_parser.mly0000644000246300004300000000546413422556306015616 0ustar filliatrvals/* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). */ /*i $Id$ i*/ /*s In actions, we reuse the location type for lex files. */ %{ open Lex_syntax open Yacc_syntax let dummy_loc = { start_pos = Lexing.dummy_pos; end_pos = Lexing.dummy_pos; start_line = 0 ; start_col = 0 } %} /*s Yacc tokens. */ %token Ttoken Tstart Ttype Tleft Tright Tnonassoc Tprec Terror %token Tident %token Taction Ttypedecl %token Tor Tsemicolon Tcolon Tmark %token EOF %start yacc_definitions %type yacc_definitions %% /*s Start symbol for yacc description files */ yacc_definitions: | header tokendecls Tmark rules header EOF { { header = $1 ; decls = $2; rules = $4; trailer = $5 } } ; header : | Taction { $1 } | /* $\varepsilon$ */ { dummy_loc } ; /*s Token declarations. */ tokendecls : | tokendecl tokendecls { $1::$2 } | /*epsilon*/ { [] } ; tokendecl : | Ttoken Ttypedecl idlist { Typed_tokens($2,$3) } | Ttoken idlist { Untyped_tokens($2) } | Ttype Ttypedecl idlist { Non_terminals_type($2,$3) } | Tstart idlist { Start_symbols($2) } | Tleft idlist { Tokens_assoc($2) } | Tnonassoc idlist { Tokens_assoc($2) } | Tright idlist { Tokens_assoc($2) } ; idlist: | Tident { [$1] } | Tident idlist { $1 :: $2 } ; /*s Parsing of rules. */ rules: | /* $\varepsilon$ */ { [] } | general_rule rules { $1 :: $2 } ; /* Ocamlyacc manual asks for a semicolon at end of each rules. But ocamlyacc accepts if they are missing. We issue a warning for non conformity to ocamlyacc documentation. */ general_rule: | rule Tsemicolon { $1 } | rule { Yacc_syntax.issue_warning "ocamlyacc documentation recommends adding a semicolon at end of each grammar rules"; $1 } ; rule : | Tident Tcolon right_part { ($1,$3) } | Tident Tcolon Tor right_part { ($1,$4) } ; right_part : | word Taction { [($1,$2)] } | word Taction Tor right_part { ($1,$2) :: $4 } ; word : | /* $\varepsilon$ */ { [] } | Tident word { $1 :: $2 } | Tprec Tident word { $2 :: $3 } | Terror word { $2 } ; ocamlweb-1.41/yacc_syntax.ml0000644000246300004300000000340713422556306015452 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (* $Id$ *) (*s locations for refering to CAML parts of yacc files *) type location = Lex_syntax.location type ident = string * location type token_decls = | Typed_tokens of location * ident list (*r \verb|%token ...| *) | Untyped_tokens of ident list (*r \verb|%token ...| *) | Non_terminals_type of location * ident list (*r \verb|%type ...| *) | Start_symbols of ident list (*r \verb|%start ...| *) | Tokens_assoc of ident list (*r \verb|%left|, \verb|%right| or \verb|%nonassoc| *) type yacc_definitions = { header : location ; decls : token_decls list; rules : (ident * (ident list * location) list) list ; trailer : location } let current_file_name = ref "" let current_line_num = ref 0 let current_line_start_pos = ref 0 let current_lexbuf = ref (Lexing.from_string "") let issue_warning msg = if not !Output.quiet then let line = !current_line_num and column = Lexing.lexeme_start !current_lexbuf - !current_line_start_pos in Printf.eprintf "Warning in file %s at line %d, character %d: %s\n" !current_file_name line column msg ocamlweb-1.41/yacc_syntax.mli0000644000246300004300000000307013422556306015617 0ustar filliatrvals(* * ocamlweb - A WEB-like tool for ocaml * Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ * * This software is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License version 2, as published by the Free Software Foundation. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU Library General Public License version 2 for more details * (enclosed in the file LGPL). *) (* $Id$ *) (* locations for refering to CAML parts of yacc files *) type location = Lex_syntax.location type ident = string * location type token_decls = | Typed_tokens of location * ident list (*r \verb|%token ...| *) | Untyped_tokens of ident list (*r \verb|%token ...| *) | Non_terminals_type of location * ident list (*r \verb|%type ...| *) | Start_symbols of ident list (*r \verb|%start ...| *) | Tokens_assoc of ident list (*r \verb|%left|, \verb|%right| or \verb|%nonassoc| *) type yacc_definitions = { header : location ; decls : token_decls list; rules : (ident * (ident list * location) list) list ; trailer : location } (* current file being parsed, current lexer buffer, *) val current_file_name : string ref val current_line_num : int ref val current_line_start_pos : int ref val current_lexbuf : Lexing.lexbuf ref val issue_warning : string -> unit ocamlweb-1.41/ocamlweb.sty0000644000246300004300000001601513422556306015124 0ustar filliatrvals% This is ocamlweb.sty, by Jean-Christophe Filliâtre % modified by Claude Marché % This LaTeX package is used by ocamlweb (http://www.lri.fr/~filliatr/ocamlweb) % % You can modify the following macros to customize the appearance % of the document. \newif\iflatexsectioning\latexsectioningfalse % the following comment tells HeVeA to ignore all this until END LATEX %BEGIN LATEX \NeedsTeXFormat{LaTeX2e} \ProvidesPackage{ocamlweb}[1999/05/21] % package options % option for the sectioning style % if false, the sectioning is similar to the web sectioning, sections % numbered in sequences. If true, structured sectioning is allowed % using LaTeX sectioning commands. \DeclareOption{noweb}{\latexsectioningtrue} \DeclareOption{web-sects}{\latexsectioningfalse} % option for visible spaces \newif\ifvisiblespaces\visiblespacestrue \DeclareOption{novisiblespaces}{\visiblespacesfalse} % option for index by pages \newif\ifbypage\bypagetrue \DeclareOption{bypages}{\bypagetrue} \DeclareOption{bysections}{\bypagefalse} \ProcessOptions % needed to make hypertex work \AtBeginDocument{\let\Hy@tempa\relax} %END LATEX % HeVeA reads the following % Hevea puts to much space with \medskip and \bigskip %HEVEA\renewcommand{\medskip}{} %HEVEA\renewcommand{\bigskip}{} % own name \newcommand{\ocamlweb}{\textsf{ocamlweb}} % pretty underscores (the package fontenc causes ugly underscores) %BEGIN LATEX \def\_{\kern.08em\vbox{\hrule width.35em height.6pt}\kern.08em} %END LATEX % Bigger underscore for ocamllex files (lexers). \newcommand{\ocwlexwc}{\textnormal{\large \_\,}} % macro for typesetting ocamllex keywords and for regexp and rule idents \newcommand{\ocwlexkw}[1]{\textsf{#1}} \newcommand{\ocwlexident}[1]{\ensuremath{\mathit{#1\/}}} % macro for typesetting ocamlyacc keywords and for non-terminals and tokens \newcommand{\ocwyacckw}[1]{\textsf{#1}} \newcommand{\ocwyaccident}[1]{\ensuremath{\mathit{#1\/}}} % macro for typesetting keywords \newcommand{\ocwkw}[1]{\textsf{#1}} % macro for typesetting base types (int, bool, string, etc.) \newcommand{\ocwbt}[1]{\textit{#1\/}} % macro for typesetting type variables \newcommand{\ocwtv}[1]{\textit{'#1\/}} % macro for typesetting identifiers \newcommand{\ocwsymbolid}[1]{{#1}} \newcommand{\ocwlowerid}[1]{\ensuremath{\mathit{#1\/}}} \newcommand{\ocwupperid}[1]{\ensuremath{\mathit{#1\/}}} % macros for typesetting constants \newcommand{\ocwhexconst}[1]{\ensuremath{\mathtt{#1}_{16}}} \newcommand{\ocwoctconst}[1]{\ensuremath{#1_8}} \newcommand{\ocwbinconst}[1]{\ensuremath{#1_2}} \newcommand{\ocwfloatconst}[2]{\ensuremath{#1\cdot 10^{#2}}} \newcommand{\ocwfloatconstexp}[1]{\ensuremath{10^{#1}}} % newline, and indentation %BEGIN LATEX \newcommand{\ocweol}{\setlength\parskip{0pt}\par\penalty5000} \newcommand{\ocwindent}[1]{\noindent\kern#1} %END LATEX %HEVEA\newcommand{\ocweol}{\begin{rawhtml}
\end{rawhtml}} %HEVEA\newcommand{\ocwindent}[1]{\hspace{#1}\hspace{#1}} % macro for typesetting comments \newcommand{\ocwbc}{\ensuremath{(\ast}} \newcommand{\ocwec}{\ensuremath{\ast)}} % yacc comments \newcommand{\ocwbyc}{\ensuremath{/\ast}} \newcommand{\ocweyc}{\ensuremath{\ast/}} % yacc special notations \iflatexsectioning \newcommand{\ocwyaccrules}{\subsection*{Grammar rules}} \newcommand{\ocwyacctrailer}{\subsection*{Trailer}} \newcommand{\ocwyaccopercentbrace}{\subsection*{Header}} \newcommand{\ocwyacccpercentbrace}{\subsection*{Token declarations}} \else \newcommand{\ocwyaccrules}{} \newcommand{\ocwyacctrailer}{} \newcommand{\ocwyaccopercentbrace}{} \newcommand{\ocwyacccpercentbrace}{} \fi \newcommand{\ocwyacccolon}{\ensuremath{::=}} \newcommand{\ocwyaccendrule}{} \newcommand{\ocwyaccpipe}{\ensuremath{\mid}} %BEGIN LATEX \newbox\boxA \newbox\boxB \newdimen\boxwidth \def\ocwcomment{\unskip\hskip 2em\null\par\nointerlineskip \setbox\boxA=\lastbox \setbox\boxB=\hbox{\strut\unhbox\boxA}\boxwidth=\wd\boxB \noindent\box\boxB\par \ifdim\boxwidth<.5\hsize\vskip -\baselineskip \else\boxwidth=.5\hsize\fi \noindent\hangafter=0 \hangindent=\boxwidth \llap{$(*$ }\ignorespaces} \def\ocwendcomment{\unskip~$*)$\strut\par} %END LATEX %HEVEA\newcommand{\ocwcomment}{(*} %HEVEA\newcommand{\ocwendcomment}{*)} %BEGIN LATEX \def\ocwbegincode{} \def\ocwendcode{} \def\ocwbegindcode{} \def\ocwenddcode{} %END LATEX %HEVEA\newcommand{\ocwbegincode}{} %HEVEA\newcommand{\ocwendcode}{} %HEVEA\newcommand{\ocwbegindcode}{} %HEVEA\newcommand{\ocwenddcode}{} %HEVEA\newcommand{\endgraf}{} \newcommand{\ocwstring}[1]{\texttt{#1}} % visible space in a string %BEGIN LATEX \ifvisiblespaces \newcommand{\ocwvspace}{\texttt{\char`\ }} \else \newcommand{\ocwvspace}{\texttt{~}} \fi %END LATEX %HEVEA\newcommand{\ocwvspace}{\hspace{1em}} % macro to insert a title and to set the header accordingly %BEGIN LATEX \def\currentmodule{} \newcommand{\ocwheader}[1]{\gdef\currentmodule{#1}} \newcommand{\ocwtitle}[1]{% \section*{#1}% \def\currentmodule{#1}% \addtocounter{ocwcounter}{1}% \markboth{}{#1 \hfill {\rm\S\theocwcounter}\quad}% \addtocounter{ocwcounter}{-1}% } %END LATEX %HEVEA\newcommand{\ocwtitle}[1]{\section*{#1}} % macro for typesetting the title of a module implementation \newcommand{\ocwmodule}[1]{\ocwtitle{Module #1}} % macro for typesetting the title of a module interface \newcommand{\ocwinterface}[1]{\ocwtitle{Interface for module #1}} % interface part of a module \newcommand{\ocwinterfacepart}{\subsection*{Interface}} % code part of a module \newcommand{\ocwcodepart}{\subsection*{Code}} % macro for typesetting the title of a lex description \newcommand{\ocwlexmodule}[1]{\ocwtitle{Module #1 (Lex)}} % macro for typesetting the title of a yacc description \newcommand{\ocwyaccmodule}[1]{\ocwtitle{Module #1 (Yacc)}} % new WEB section \newcounter{ocwcounter} \setcounter{ocwcounter}{0} \newcommand{\ocwsection}{% \refstepcounter{ocwcounter}% \bigskip\noindent{\bf\theocwcounter.}% %BEGIN LATEX \markboth{}{\currentmodule \hfill {\rm\S\theocwcounter}\quad}% \kern1em% %END LATEX %HEVEA\hspace{1em} } %HEVEA\newcommand{\currentmodule}{} % index %BEGIN LATEX \newcommand{\ocwbeginindex}{% \markboth{}{Index \hfill {\rm\S\theocwcounter}\quad}% \begin{theindex}% }% \newcommand{\ocwendindex}{\end{theindex}} %END LATEX %HEVEA\newcommand{\ocwbeginindex}{\section{Index}\begin{itemize}} %HEVEA\newcommand{\ocwendindex}{\end{itemize}} % index entry in web-sects option \newcommand{\ocwwebindexentry}[3]{\item #1,\quad#2#3} % index entry in noweb option %BEGIN LATEX \def\loopbody{% \edef\ocwnext{% \@ifundefined{r@\ocwloop}{??}{\ifbypage\pageref{\ocwloop}\else \ref{\ocwloop}\fi}}% \ifx\ocwprevious\ocwnext\relax \else \ocwsep\ocwoutputref{\ocwnext}% \edef\ocwprevious{\ocwnext}% \def\ocwsep{, }% \fi} \newcommand{\ocwrefindexentry}[5]{\item #1,\quad \def\ocwsep{\relax}% \def\ocwoutputref{\textbf}% \def\ocwprevious{0}% \@for\ocwloop:=#2\do{\loopbody}% \def\ocwoutputref{\textrm}% \def\ocwprevious{0}% \@for\ocwloop:=#3\do{\loopbody}% } %END LATEX %HEVEA\newcommand{\ocwrefindexentry}[5]{\item #1,\quad#4, #5} %HEVEA\newcommand{\lnot}{\ocwkw{not}} %HEVEA\newcommand{\lor}{\ocwkw{or}} %HEVEA\newcommand{\land}{\&} %HEVEA\newcommand{\markboth}{}{} ocamlweb-1.41/bootstrap.tex0000644000246300004300000000150213422556306015324 0ustar filliatrvals \newcommand{\ocaml}{\textsf{Objective Caml}} \ocwsection This is \ocamlweb, a literate programming tool for \ocaml. This document has been automatically produced using \ocamlweb\ itself, applied to his own code, in some kind of `bootstrap'. This code is split into several OCaml modules, organized as follows: \begin{center} \begin{tabular}{|l|l|} \hline \bf Module & \bf Function \\ \hline\hline Output & Low level printing functions, independent of the document type \\ \hline Cross & Cross references in Caml files \\ \hline Pretty & Pretty-print of code and documentation \\ \hline Web & Production of the whole document, including the index \\ \hline Doclexer& Lexer to separate code and doc parts in Caml files \\ \hline Main & Main program \\ \hline \end{tabular} \end{center} ocamlweb-1.41/Makefile.in0000644000246300004300000001727513422556306014650 0ustar filliatrvals # where to install the binaries prefix=@prefix@ exec_prefix=@exec_prefix@ BINDIR=@bindir@ # where to install the man page MANDIR=@mandir@ # where to install the style file BASETEXDIR = $(prefix)/share/texmf TEXDIR = $(BASETEXDIR)/tex/latex/misc # command to update TeX' kpathsea database MKTEXLSR = @MKTEXLSR@ UPDATETEX = $(MKTEXLSR) /usr/share/texmf /var/spool/texmf $(BASETEXDIR) > /dev/null # Version # ATTENTION A BIEN UTILISER UN NUMERO DE VERSION DE LA FORME X.YY # (requete de Ralf pour la Debian) MAJORVN=1 MINORVN=41 VERSION=$(MAJORVN).$(MINORVN) OCAMLBEST=@OCAMLBEST@ CAMLC = @OCAMLC@ CAMLCOPT = @OCAMLOPT@ CAMLDEP = @OCAMLDEP@ ZLIBS = -I ocaml-parser -I ocamllex-parser DEBUG = PROFILE = BYTEFLAGS= $(ZLIBS) $(DEBUG) OPTFLAGS = $(ZLIBS) $(PROFILE) CAML_CMO = ocaml-parser/misc.cmo ocaml-parser/clflags.cmo \ ocaml-parser/terminfo.cmo ocaml-parser/warnings.cmo \ ocaml-parser/linenum.cmo ocaml-parser/location.cmo \ ocaml-parser/longident.cmo \ ocaml-parser/syntaxerr.cmo ocaml-parser/parser.cmo \ ocaml-parser/lexer.cmo ocaml-parser/parse.cmo CAML_CMX = $(CAML_CMO:.cmo=.cmx) CAMLLEX_CMO = ocamllex-parser/lex_parser.cmo ocamllex-parser/lex_lexer.cmo CAMLLEX_CMX = $(CAMLLEX_CMO:.cmo=.cmx) CMO = output.cmo yacc_syntax.cmo yacc_parser.cmo yacc_lexer.cmo cross.cmo pretty.cmo \ web.cmo doclexer.cmo \ version.cmo main.cmo CMX = $(CMO:.cmo=.cmx) all: @OCAMLBEST@ opt: ocamlweb byte: ocamlweb.byte ocamlweb: $(CAML_CMX) $(CAMLLEX_CMX) $(CMX) $(CAMLCOPT) $(OPTFLAGS) -o $@ -I +compiler-libs ocamloptcomp.cmxa $(CAML_CMX) $(CAMLLEX_CMX) $(CMX) strip ocamlweb ocamlweb.byte: $(CAML_CMO) $(CAMLLEX_CMO) $(CMO) $(CAMLC) $(BYTEFLAGS) -o $@ $(CAML_CMO) $(CAMLLEX_CMO) $(CMO) ocamlweb.static: $(CAML_CMX) $(CAMLLEX_CMX) $(CMX) $(CAMLCOPT) $(OPTFLAGS) -cclib -static -o $@ $(CAML_CMX) $(CAMLLEX_CMX) $(CMX) strip $@ debug: $(CAML_CMO) $(CAMLLEX_CMO) $(CMO) $(CAMLC) $(BYTEFLAGS) -o ocamlweb-debug $(CAML_CMO) $(CAMLLEX_CMO) $(CMO) version.ml: Makefile echo "let version = \""$(VERSION)"\"" > version.ml echo "let date = \""`date`"\"" >> version.ml install-indep: mkdir -p $(BINDIR) mkdir -p $(MANDIR)/man1 cp doc/ocamlweb.1 $(MANDIR)/man1 mkdir -p $(TEXDIR) cp ocamlweb.sty $(TEXDIR) $(UPDATETEX) install: install-indep if test @OCAMLBEST@ = opt ; then \ cp ocamlweb $(BINDIR) ; \ else \ cp ocamlweb.byte $(BINDIR)/ocamlweb ; \ fi install-byte: install-indep cp ocamlweb.byte $(BINDIR)/ocamlweb local: ocamlweb cp ocamlweb $$HOME/bin/$$OSTYPE cp doc/ocamlweb.1 $$HOME/man/man1 cp ocamlweb.sty $$HOME/tex/inputs install-demons: ocamlweb.static cp ocamlweb.static /users/demons/demons/bin/$$OSTYPE/ocamlweb cp doc/ocamlweb.1 /users/demons/demons/man/man1 cp ocamlweb.sty /users/demons/demons/tex/inputs manual: make -C doc VERSION=$(VERSION) all LATEX=TEXINPUTS=..: ; export TEXINPUTS ; latex PDFLATEX=TEXINPUTS=..: ; export TEXINPUTS ; pdflatex TESTFILES=test/test.mli test/test.ml test/test_lex.mll test/test_yacc.mly test/test.tex: ocamlweb $(TESTFILES) ./ocamlweb $(TESTFILES) -o test/test.tex .PHONY: test test: ocamlweb.sty test/test.tex cd test; $(PDFLATEX) test cd test ; grep -q "Rerun" test.log && ($(PDFLATEX) test) || true - cd test ; hevea -o test.html ../ocamlweb.sty test.tex evince test/test.pdf BOOTSTRAP= bootstrap.tex output.mli output.ml \ yacc_parser.mly yacc_lexer.mll cross.mli cross.ml \ pretty.mli pretty.mll \ web.mli web.ml doclexer.mli doclexer.mll main.ml bootstrap: ocamlweb ./ocamlweb -o test/ocamlweb.tex $(BOOTSTRAP) cd test; $(PDFLATEX) ./ocamlweb cd test; grep -q "Rerun" ocamlweb.log && ($(PDFLATEX) ./ocamlweb) || true - cd test; hevea -o ocamlweb.html ../ocamlweb.sty ocamlweb.tex check: bootstrap # export ######## NAME=ocamlweb-$(VERSION) FTP = $(HOME)/ftp/ocamlweb WWW = $(HOME)/WWW/ocamlweb FILES = *.ml* ocamlweb.sty bootstrap.tex \ Makefile.in configure.in configure .depend \ README INSTALL COPYING LGPL CHANGES OCAMLFILES = misc.mli misc.ml clflags.ml \ terminfo.mli terminfo.ml \ warnings.mli warnings.ml \ linenum.mli linenum.mll \ location.mli location.ml \ longident.mli longident.ml \ syntaxerr.mli syntaxerr.ml \ asttypes.mli parsetree.mli \ parser.mly \ lexer.mli lexer.mll \ parse.mli parse.ml \ README LICENSE OCAMLLEXFILES = lex_syntax.mli lex_parser.mly lex_lexer.mll DOCFILES = doc/$(NAME)-man.tex doc/$(NAME)-man.html doc/ocamlweb.1 export: source linux cp README COPYING LGPL CHANGES $(FTP) make -C doc VERSION=$(VERSION) all export make export-bootstrap mail -s "nouvelle release d'ocamlweb" treinen@debian.org < /dev/null export-bootstrap: bootstrap gzip -c test/ocamlweb.ps > $(FTP)/ocamlweb.ps.gz cp test/ocamlweb.html $(FTP) source: clean manual mkdir -p export/$(NAME)/test cd export/$(NAME); mkdir -p ocaml-parser; mkdir -p ocamllex-parser; mkdir -p test; \ mkdir -p doc; mkdir -p support cp $(FILES) export/$(NAME) cp $(DOCFILES) export/$(NAME)/doc cd ocaml-parser; cp $(OCAMLFILES) ../export/$(NAME)/ocaml-parser cd ocamllex-parser; cp $(OCAMLLEXFILES) ../export/$(NAME)/ocamllex-parser cd support; cp config.guess config.sub install-sh \ ../export/$(NAME)/support cd export ; tar cf $(NAME).tar $(NAME) ; \ gzip -f --best $(NAME).tar cp export/$(NAME).tar.gz $(FTP) BINARY = $(NAME)-$(OSTYPE) linux: clean binary solaris: rmake sun-demons $(HOME)/soft/ocaml/ocamlweb clean binary BINARYFILES = README INSTALL COPYING LGPL ocamlweb ocamlweb.sty binary: ocamlweb manual mkdir -p export/$(BINARY)/doc cp $(BINARYFILES) export/$(BINARY) cp $(DOCFILES) export/$(BINARY)/doc (cd export; tar czf $(BINARY).tar.gz $(BINARY)) cp export/$(BINARY).tar.gz $(FTP) # generic rules : ################# .SUFFIXES: .mli .ml .cmi .cmo .cmx .mll .mll.ml: ocamllex $< .mli.cmi: $(CAMLC) -c $(BYTEFLAGS) $< .ml.cmo: $(CAMLC) -c $(BYTEFLAGS) $< .ml.o: $(CAMLCOPT) -c $(OPTFLAGS) $< .ml.cmx: $(CAMLCOPT) -c $(OPTFLAGS) $< ocaml-parser/parser.mli ocaml-parser/parser.ml: ocaml-parser/parser.mly ocamlyacc -v ocaml-parser/parser.mly yacc_parser.mli yacc_parser.ml: yacc_parser.mly ocamlyacc -v yacc_parser.mly ocamllex-parser/lex_parser.mli ocamllex-parser/lex_parser.ml: ocamllex-parser/lex_parser.mly ocamlyacc -v ocamllex-parser/lex_parser.mly # Emacs tags ############ tags: etags "--regex=/let[ \t]+\([^ \t]+\)/\1/" \ "--regex=/let[ \t]+rec[ \t]+\([^ \t]+\)/\1/" \ "--regex=/and[ \t]+\([^ \t]+\)/\1/" \ "--regex=/type[ \t]+\([^ \t]+\)/\1/" \ "--regex=/exception[ \t]+\([^ \t]+\)/\1/" \ "--regex=/val[ \t]+\([^ \t]+\)/\1/" \ "--regex=/module[ \t]+\([^ \t]+\)/\1/" *.mli *.ml # myself Makefile: Makefile.in config.status ./config.status config.status: configure ./config.status --recheck configure: configure.in autoconf # clean and depend ################## GENERATED = doclexer.ml pretty.ml version.ml yacc_lexer.ml \ yacc_parser.ml yacc_parser.mli yacc_parser.output \ ocaml-parser/lexer.ml ocaml-parser/linenum.ml \ ocaml-parser/parser.mli ocaml-parser/parser.ml \ ocamllex-parser/lex_lexer.ml ocamllex-parser/lex_parser.ml \ ocamllex-parser/lex_parser.mli clean: rm -f *~ *.cm[iox] *.o rm -f ocaml-parser/*~ ocaml-parser/*.cm[iox] ocaml-parser/*.o rm -f ocamllex-parser/*~ ocamllex-parser/*.cm[iox] ocamllex-parser/*.o rm -f ocamlweb ocamlweb.byte rm -f $(GENERATED) rm -f yacc-parser.output ocaml-parser/parser.output rm -f ocamllex-parser/lex_parser.output cd test; rm -f *.aux *.log *.dvi *.ps *.tex dist-clean:: clean rm -f Makefile rm -f config.status config.cache config.log depend: $(GENERATED) rm -f .depend ocamldep $(ZLIBS) *.mli *.ml ocaml-parser/*.ml ocaml-parser/*.mli ocamllex-parser/*.ml ocamllex-parser/*.mli > .depend include .depend ocamlweb-1.41/configure.in0000644000246300004300000000477413422556306015114 0ustar filliatrvals# autoconf input for ocamlweb # check for one particular file of the sources AC_INIT(web.mli) # Check for Ocaml compilers # we first look for ocamlc in the path; if not present, we abort AC_CHECK_PROG(OCAMLC,ocamlc,ocamlc,no) if test "$OCAMLC" = no ; then AC_MSG_ERROR(Cannot find ocamlc.) fi # we extract Ocaml version number and library path OCAMLVERSION=`$OCAMLC -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` echo "ocaml version is $OCAMLVERSION" OCAMLLIB=`$OCAMLC -v | tail -1 | cut -f 4 -d " "` echo "ocaml library path is $OCAMLLIB" # then we look for ocamlopt; if not present, we issue a warning # if the version is not the same, we also discard it # we set OCAMLBEST to "opt" or "byte", whether ocamlopt is available or not AC_CHECK_PROG(OCAMLOPT,ocamlopt,ocamlopt,no) OCAMLBEST=byte if test "$OCAMLOPT" = no ; then AC_MSG_WARN(Cannot find ocamlopt; bytecode compilation only.) else AC_MSG_CHECKING(ocamlopt version) TMPVERSION=`$OCAMLOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVERSION" != $OCAMLVERSION ; then AC_MSG_RESULT(differs from ocamlc; ocamlopt discarded.) OCAMLOPT=no else AC_MSG_RESULT(ok) OCAMLBEST=opt fi fi # checking for ocamlc.opt AC_CHECK_PROG(OCAMLCDOTOPT,ocamlc.opt,ocamlc.opt,no) if test "$OCAMLCDOTOPT" != no ; then AC_MSG_CHECKING(ocamlc.opt version) TMPVERSION=`$OCAMLCDOTOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVERSION" != $OCAMLVERSION ; then AC_MSG_RESULT(differs from ocamlc; ocamlc.opt discarded.) else AC_MSG_RESULT(ok) OCAMLC=$OCAMLCDOTOPT fi fi # checking for ocamlopt.opt if test "$OCAMLOPT" != no ; then AC_CHECK_PROG(OCAMLOPTDOTOPT,ocamlopt.opt,ocamlopt.opt,no) if test "$OCAMLOPTDOTOPT" != no ; then AC_MSG_CHECKING(ocamlc.opt version) TMPVER=`$OCAMLOPTDOTOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVER" != $OCAMLVERSION ; then AC_MSG_RESULT(differs from ocamlc; ocamlopt.opt discarded.) else AC_MSG_RESULT(ok) OCAMLOPT=$OCAMLOPTDOTOPT fi fi fi # ocamldep should also be present in the path AC_CHECK_PROG(OCAMLDEP,ocamldep,ocamldep,no) if test "$OCAMLC" = no ; then AC_MSG_ERROR(Cannot find ocamldep.) fi # substitutions to perform AC_SUBST(OCAMLC) AC_SUBST(OCAMLOPT) AC_SUBST(OCAMLDEP) AC_SUBST(OCAMLBEST) AC_SUBST(OCAMLVERSION) AC_SUBST(OCAMLLIB) AC_PATH_PROG(MKTEXLSR,mktexlsr,true) if test "$MKTEXLSR" = true ; then AC_MSG_WARN(Cannot find mktexlsr.) fi AC_SUBST(MKTEXLSR) # Finally create all the generated files AC_OUTPUT(Makefile) chmod a-w Makefile ocamlweb-1.41/configure0000755000246300004300000026554213422556306014514 0ustar filliatrvals#! /bin/sh # Guess values for system-dependent variables and create Makefiles. # Generated by GNU Autoconf 2.69. # # # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. # # # This configure script is free software; the Free Software Foundation # gives unlimited permission to copy, distribute and modify it. ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # Use a proper internal environment variable to ensure we don't fall # into an infinite loop, continuously re-executing ourselves. if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then _as_can_reexec=no; export _as_can_reexec; # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 as_fn_exit 255 fi # We don't want this to propagate to other subprocesses. { _as_can_reexec=; unset _as_can_reexec;} if test "x$CONFIG_SHELL" = x; then as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which # is contrary to our usage. Disable this feature. alias -g '\${1+\"\$@\"}'='\"\$@\"' setopt NO_GLOB_SUBST else case \`(set -o) 2>/dev/null\` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi " as_required="as_fn_return () { (exit \$1); } as_fn_success () { as_fn_return 0; } as_fn_failure () { as_fn_return 1; } as_fn_ret_success () { return 0; } as_fn_ret_failure () { return 1; } exitcode=0 as_fn_success || { exitcode=1; echo as_fn_success failed.; } as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; } as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; } as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; } if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then : else exitcode=1; echo positional parameters were not saved. fi test x\$exitcode = x0 || exit 1 test -x / || exit 1" as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1" if (eval "$as_required") 2>/dev/null; then : as_have_required=yes else as_have_required=no fi if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then : else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR as_found=false for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. as_found=: case $as_dir in #( /*) for as_base in sh bash ksh sh5; do # Try only shells that exist, to save several forks. as_shell=$as_dir/$as_base if { test -f "$as_shell" || test -f "$as_shell.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then : CONFIG_SHELL=$as_shell as_have_required=yes if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then : break 2 fi fi done;; esac as_found=false done $as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then : CONFIG_SHELL=$SHELL as_have_required=yes fi; } IFS=$as_save_IFS if test "x$CONFIG_SHELL" != x; then : export CONFIG_SHELL # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 exit 255 fi if test x$as_have_required = xno; then : $as_echo "$0: This script requires a shell more modern than all" $as_echo "$0: the shells that I found on your system." if test x${ZSH_VERSION+set} = xset ; then $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should" $as_echo "$0: be upgraded to zsh 4.3.4 or later." else $as_echo "$0: Please tell bug-autoconf@gnu.org about your system, $0: including any error possibly output before this $0: message. Then install a modern shell, or manually run $0: the script under such a shell if you do have one." fi exit 1 fi fi fi SHELL=${CONFIG_SHELL-/bin/sh} export SHELL # Unset more variables known to interfere with behavior of common tools. CLICOLOR_FORCE= GREP_OPTIONS= unset CLICOLOR_FORCE GREP_OPTIONS ## --------------------- ## ## M4sh Shell Functions. ## ## --------------------- ## # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits as_lineno_1=$LINENO as_lineno_1a=$LINENO as_lineno_2=$LINENO as_lineno_2a=$LINENO eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" && test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || { # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-) sed -n ' p /[$]LINENO/= ' <$as_myself | sed ' s/[$]LINENO.*/&-/ t lineno b :lineno N :loop s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/ t loop s/-\n.*// ' >$as_me.lineno && chmod +x "$as_me.lineno" || { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } # If we had to re-execute with $CONFIG_SHELL, we're ensured to have # already done that, so ensure we don't try to do so again and fall # in an infinite loop. This has already happened in practice. _as_can_reexec=no; export _as_can_reexec # Don't try to exec as it changes $[0], causing all sort of problems # (the dirname of $[0] is not the place where we might find the # original and so on. Autoconf is especially sensitive to this). . "./$as_me.lineno" # Exit status is that of the last command. exit } ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" test -n "$DJDIR" || exec 7<&0 &1 # Name of the host. # hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status, # so uname gets run too. ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` # # Initializations. # ac_default_prefix=/usr/local ac_clean_files= ac_config_libobj_dir=. LIBOBJS= cross_compiling=no subdirs= MFLAGS= MAKEFLAGS= # Identity of this package. PACKAGE_NAME= PACKAGE_TARNAME= PACKAGE_VERSION= PACKAGE_STRING= PACKAGE_BUGREPORT= PACKAGE_URL= ac_unique_file="web.mli" ac_subst_vars='LTLIBOBJS LIBOBJS MKTEXLSR OCAMLLIB OCAMLVERSION OCAMLBEST OCAMLDEP OCAMLOPTDOTOPT OCAMLCDOTOPT OCAMLOPT OCAMLC target_alias host_alias build_alias LIBS ECHO_T ECHO_N ECHO_C DEFS mandir localedir libdir psdir pdfdir dvidir htmldir infodir docdir oldincludedir includedir localstatedir sharedstatedir sysconfdir datadir datarootdir libexecdir sbindir bindir program_transform_name prefix exec_prefix PACKAGE_URL PACKAGE_BUGREPORT PACKAGE_STRING PACKAGE_VERSION PACKAGE_TARNAME PACKAGE_NAME PATH_SEPARATOR SHELL' ac_subst_files='' ac_user_opts=' enable_option_checking ' ac_precious_vars='build_alias host_alias target_alias' # Initialize some variables set by options. ac_init_help= ac_init_version=false ac_unrecognized_opts= ac_unrecognized_sep= # The variables have the same names as the options, with # dashes changed to underlines. cache_file=/dev/null exec_prefix=NONE no_create= no_recursion= prefix=NONE program_prefix=NONE program_suffix=NONE program_transform_name=s,x,x, silent= site= srcdir= verbose= x_includes=NONE x_libraries=NONE # Installation directory options. # These are left unexpanded so users can "make install exec_prefix=/foo" # and all the variables that are supposed to be based on exec_prefix # by default will actually change. # Use braces instead of parens because sh, perl, etc. also accept them. # (The list follows the same order as the GNU Coding Standards.) bindir='${exec_prefix}/bin' sbindir='${exec_prefix}/sbin' libexecdir='${exec_prefix}/libexec' datarootdir='${prefix}/share' datadir='${datarootdir}' sysconfdir='${prefix}/etc' sharedstatedir='${prefix}/com' localstatedir='${prefix}/var' includedir='${prefix}/include' oldincludedir='/usr/include' docdir='${datarootdir}/doc/${PACKAGE}' infodir='${datarootdir}/info' htmldir='${docdir}' dvidir='${docdir}' pdfdir='${docdir}' psdir='${docdir}' libdir='${exec_prefix}/lib' localedir='${datarootdir}/locale' mandir='${datarootdir}/man' ac_prev= ac_dashdash= for ac_option do # If the previous option needs an argument, assign it. if test -n "$ac_prev"; then eval $ac_prev=\$ac_option ac_prev= continue fi case $ac_option in *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;; *=) ac_optarg= ;; *) ac_optarg=yes ;; esac # Accept the important Cygnus configure options, so we can diagnose typos. case $ac_dashdash$ac_option in --) ac_dashdash=yes ;; -bindir | --bindir | --bindi | --bind | --bin | --bi) ac_prev=bindir ;; -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) bindir=$ac_optarg ;; -build | --build | --buil | --bui | --bu) ac_prev=build_alias ;; -build=* | --build=* | --buil=* | --bui=* | --bu=*) build_alias=$ac_optarg ;; -cache-file | --cache-file | --cache-fil | --cache-fi \ | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) ac_prev=cache_file ;; -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) cache_file=$ac_optarg ;; --config-cache | -C) cache_file=config.cache ;; -datadir | --datadir | --datadi | --datad) ac_prev=datadir ;; -datadir=* | --datadir=* | --datadi=* | --datad=*) datadir=$ac_optarg ;; -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \ | --dataroo | --dataro | --datar) ac_prev=datarootdir ;; -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \ | --dataroot=* | --dataroo=* | --dataro=* | --datar=*) datarootdir=$ac_optarg ;; -disable-* | --disable-*) ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=no ;; -docdir | --docdir | --docdi | --doc | --do) ac_prev=docdir ;; -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*) docdir=$ac_optarg ;; -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv) ac_prev=dvidir ;; -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*) dvidir=$ac_optarg ;; -enable-* | --enable-*) ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=\$ac_optarg ;; -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ | --exec | --exe | --ex) ac_prev=exec_prefix ;; -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ | --exec=* | --exe=* | --ex=*) exec_prefix=$ac_optarg ;; -gas | --gas | --ga | --g) # Obsolete; use --with-gas. with_gas=yes ;; -help | --help | --hel | --he | -h) ac_init_help=long ;; -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) ac_init_help=recursive ;; -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) ac_init_help=short ;; -host | --host | --hos | --ho) ac_prev=host_alias ;; -host=* | --host=* | --hos=* | --ho=*) host_alias=$ac_optarg ;; -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht) ac_prev=htmldir ;; -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \ | --ht=*) htmldir=$ac_optarg ;; -includedir | --includedir | --includedi | --included | --include \ | --includ | --inclu | --incl | --inc) ac_prev=includedir ;; -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ | --includ=* | --inclu=* | --incl=* | --inc=*) includedir=$ac_optarg ;; -infodir | --infodir | --infodi | --infod | --info | --inf) ac_prev=infodir ;; -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) infodir=$ac_optarg ;; -libdir | --libdir | --libdi | --libd) ac_prev=libdir ;; -libdir=* | --libdir=* | --libdi=* | --libd=*) libdir=$ac_optarg ;; -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ | --libexe | --libex | --libe) ac_prev=libexecdir ;; -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ | --libexe=* | --libex=* | --libe=*) libexecdir=$ac_optarg ;; -localedir | --localedir | --localedi | --localed | --locale) ac_prev=localedir ;; -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*) localedir=$ac_optarg ;; -localstatedir | --localstatedir | --localstatedi | --localstated \ | --localstate | --localstat | --localsta | --localst | --locals) ac_prev=localstatedir ;; -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*) localstatedir=$ac_optarg ;; -mandir | --mandir | --mandi | --mand | --man | --ma | --m) ac_prev=mandir ;; -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) mandir=$ac_optarg ;; -nfp | --nfp | --nf) # Obsolete; use --without-fp. with_fp=no ;; -no-create | --no-create | --no-creat | --no-crea | --no-cre \ | --no-cr | --no-c | -n) no_create=yes ;; -no-recursion | --no-recursion | --no-recursio | --no-recursi \ | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) no_recursion=yes ;; -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ | --oldin | --oldi | --old | --ol | --o) ac_prev=oldincludedir ;; -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) oldincludedir=$ac_optarg ;; -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) ac_prev=prefix ;; -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) prefix=$ac_optarg ;; -program-prefix | --program-prefix | --program-prefi | --program-pref \ | --program-pre | --program-pr | --program-p) ac_prev=program_prefix ;; -program-prefix=* | --program-prefix=* | --program-prefi=* \ | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) program_prefix=$ac_optarg ;; -program-suffix | --program-suffix | --program-suffi | --program-suff \ | --program-suf | --program-su | --program-s) ac_prev=program_suffix ;; -program-suffix=* | --program-suffix=* | --program-suffi=* \ | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) program_suffix=$ac_optarg ;; -program-transform-name | --program-transform-name \ | --program-transform-nam | --program-transform-na \ | --program-transform-n | --program-transform- \ | --program-transform | --program-transfor \ | --program-transfo | --program-transf \ | --program-trans | --program-tran \ | --progr-tra | --program-tr | --program-t) ac_prev=program_transform_name ;; -program-transform-name=* | --program-transform-name=* \ | --program-transform-nam=* | --program-transform-na=* \ | --program-transform-n=* | --program-transform-=* \ | --program-transform=* | --program-transfor=* \ | --program-transfo=* | --program-transf=* \ | --program-trans=* | --program-tran=* \ | --progr-tra=* | --program-tr=* | --program-t=*) program_transform_name=$ac_optarg ;; -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd) ac_prev=pdfdir ;; -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*) pdfdir=$ac_optarg ;; -psdir | --psdir | --psdi | --psd | --ps) ac_prev=psdir ;; -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*) psdir=$ac_optarg ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) silent=yes ;; -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) ac_prev=sbindir ;; -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ | --sbi=* | --sb=*) sbindir=$ac_optarg ;; -sharedstatedir | --sharedstatedir | --sharedstatedi \ | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ | --sharedst | --shareds | --shared | --share | --shar \ | --sha | --sh) ac_prev=sharedstatedir ;; -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ | --sha=* | --sh=*) sharedstatedir=$ac_optarg ;; -site | --site | --sit) ac_prev=site ;; -site=* | --site=* | --sit=*) site=$ac_optarg ;; -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) ac_prev=srcdir ;; -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) srcdir=$ac_optarg ;; -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ | --syscon | --sysco | --sysc | --sys | --sy) ac_prev=sysconfdir ;; -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) sysconfdir=$ac_optarg ;; -target | --target | --targe | --targ | --tar | --ta | --t) ac_prev=target_alias ;; -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) target_alias=$ac_optarg ;; -v | -verbose | --verbose | --verbos | --verbo | --verb) verbose=yes ;; -version | --version | --versio | --versi | --vers | -V) ac_init_version=: ;; -with-* | --with-*) ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=\$ac_optarg ;; -without-* | --without-*) ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=no ;; --x) # Obsolete; use --with-x. with_x=yes ;; -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ | --x-incl | --x-inc | --x-in | --x-i) ac_prev=x_includes ;; -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) x_includes=$ac_optarg ;; -x-libraries | --x-libraries | --x-librarie | --x-librari \ | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) ac_prev=x_libraries ;; -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) x_libraries=$ac_optarg ;; -*) as_fn_error $? "unrecognized option: \`$ac_option' Try \`$0 --help' for more information" ;; *=*) ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` # Reject names that are not valid shell variable names. case $ac_envvar in #( '' | [0-9]* | *[!_$as_cr_alnum]* ) as_fn_error $? "invalid variable name: \`$ac_envvar'" ;; esac eval $ac_envvar=\$ac_optarg export $ac_envvar ;; *) # FIXME: should be removed in autoconf 3.0. $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2 expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2 : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" ;; esac done if test -n "$ac_prev"; then ac_option=--`echo $ac_prev | sed 's/_/-/g'` as_fn_error $? "missing argument to $ac_option" fi if test -n "$ac_unrecognized_opts"; then case $enable_option_checking in no) ;; fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;; *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;; esac fi # Check all directory arguments for consistency. for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ datadir sysconfdir sharedstatedir localstatedir includedir \ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ libdir localedir mandir do eval ac_val=\$$ac_var # Remove trailing slashes. case $ac_val in */ ) ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'` eval $ac_var=\$ac_val;; esac # Be sure to have absolute directory names. case $ac_val in [\\/$]* | ?:[\\/]* ) continue;; NONE | '' ) case $ac_var in *prefix ) continue;; esac;; esac as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" done # There might be people who depend on the old broken behavior: `$host' # used to hold the argument of --host etc. # FIXME: To remove some day. build=$build_alias host=$host_alias target=$target_alias # FIXME: To remove some day. if test "x$host_alias" != x; then if test "x$build_alias" = x; then cross_compiling=maybe elif test "x$build_alias" != "x$host_alias"; then cross_compiling=yes fi fi ac_tool_prefix= test -n "$host_alias" && ac_tool_prefix=$host_alias- test "$silent" = yes && exec 6>/dev/null ac_pwd=`pwd` && test -n "$ac_pwd" && ac_ls_di=`ls -di .` && ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` || as_fn_error $? "working directory cannot be determined" test "X$ac_ls_di" = "X$ac_pwd_ls_di" || as_fn_error $? "pwd does not report name of working directory" # Find the source files, if location was not specified. if test -z "$srcdir"; then ac_srcdir_defaulted=yes # Try the directory containing this script, then the parent directory. ac_confdir=`$as_dirname -- "$as_myself" || $as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_myself" : 'X\(//\)[^/]' \| \ X"$as_myself" : 'X\(//\)$' \| \ X"$as_myself" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_myself" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` srcdir=$ac_confdir if test ! -r "$srcdir/$ac_unique_file"; then srcdir=.. fi else ac_srcdir_defaulted=no fi if test ! -r "$srcdir/$ac_unique_file"; then test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .." as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir" fi ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work" ac_abs_confdir=`( cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg" pwd)` # When building in place, set srcdir=. if test "$ac_abs_confdir" = "$ac_pwd"; then srcdir=. fi # Remove unnecessary trailing slashes from srcdir. # Double slashes in file names in object file debugging info # mess up M-x gdb in Emacs. case $srcdir in */) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;; esac for ac_var in $ac_precious_vars; do eval ac_env_${ac_var}_set=\${${ac_var}+set} eval ac_env_${ac_var}_value=\$${ac_var} eval ac_cv_env_${ac_var}_set=\${${ac_var}+set} eval ac_cv_env_${ac_var}_value=\$${ac_var} done # # Report the --help message. # if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF \`configure' configures this package to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... To assign environment variables (e.g., CC, CFLAGS...), specify them as VAR=VALUE. See below for descriptions of some of the useful variables. Defaults for the options are specified in brackets. Configuration: -h, --help display this help and exit --help=short display options specific to this package --help=recursive display the short help of all the included packages -V, --version display version information and exit -q, --quiet, --silent do not print \`checking ...' messages --cache-file=FILE cache test results in FILE [disabled] -C, --config-cache alias for \`--cache-file=config.cache' -n, --no-create do not create output files --srcdir=DIR find the sources in DIR [configure dir or \`..'] Installation directories: --prefix=PREFIX install architecture-independent files in PREFIX [$ac_default_prefix] --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX [PREFIX] By default, \`make install' will install all the files in \`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify an installation prefix other than \`$ac_default_prefix' using \`--prefix', for instance \`--prefix=\$HOME'. For better control, use the options below. Fine tuning of the installation directories: --bindir=DIR user executables [EPREFIX/bin] --sbindir=DIR system admin executables [EPREFIX/sbin] --libexecdir=DIR program executables [EPREFIX/libexec] --sysconfdir=DIR read-only single-machine data [PREFIX/etc] --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] --localstatedir=DIR modifiable single-machine data [PREFIX/var] --libdir=DIR object code libraries [EPREFIX/lib] --includedir=DIR C header files [PREFIX/include] --oldincludedir=DIR C header files for non-gcc [/usr/include] --datarootdir=DIR read-only arch.-independent data root [PREFIX/share] --datadir=DIR read-only architecture-independent data [DATAROOTDIR] --infodir=DIR info documentation [DATAROOTDIR/info] --localedir=DIR locale-dependent data [DATAROOTDIR/locale] --mandir=DIR man documentation [DATAROOTDIR/man] --docdir=DIR documentation root [DATAROOTDIR/doc/PACKAGE] --htmldir=DIR html documentation [DOCDIR] --dvidir=DIR dvi documentation [DOCDIR] --pdfdir=DIR pdf documentation [DOCDIR] --psdir=DIR ps documentation [DOCDIR] _ACEOF cat <<\_ACEOF _ACEOF fi if test -n "$ac_init_help"; then cat <<\_ACEOF Report bugs to the package provider. _ACEOF ac_status=$? fi if test "$ac_init_help" = "recursive"; then # If there are subdirs, report their specific --help. for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue test -d "$ac_dir" || { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } || continue ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix cd "$ac_dir" || { ac_status=$?; continue; } # Check for guested configure. if test -f "$ac_srcdir/configure.gnu"; then echo && $SHELL "$ac_srcdir/configure.gnu" --help=recursive elif test -f "$ac_srcdir/configure"; then echo && $SHELL "$ac_srcdir/configure" --help=recursive else $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2 fi || ac_status=$? cd "$ac_pwd" || { ac_status=$?; break; } done fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF configure generated by GNU Autoconf 2.69 Copyright (C) 2012 Free Software Foundation, Inc. This configure script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it. _ACEOF exit fi ## ------------------------ ## ## Autoconf initialization. ## ## ------------------------ ## cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. It was created by $as_me, which was generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ _ACEOF exec 5>>config.log { cat <<_ASUNAME ## --------- ## ## Platform. ## ## --------- ## hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` uname -m = `(uname -m) 2>/dev/null || echo unknown` uname -r = `(uname -r) 2>/dev/null || echo unknown` uname -s = `(uname -s) 2>/dev/null || echo unknown` uname -v = `(uname -v) 2>/dev/null || echo unknown` /usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` /bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` /bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` /usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` /usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` /usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown` /bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` /usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` /bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` _ASUNAME as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. $as_echo "PATH: $as_dir" done IFS=$as_save_IFS } >&5 cat >&5 <<_ACEOF ## ----------- ## ## Core tests. ## ## ----------- ## _ACEOF # Keep a trace of the command line. # Strip out --no-create and --no-recursion so they do not pile up. # Strip out --silent because we don't want to record it for future runs. # Also quote any args containing shell meta-characters. # Make two passes to allow for proper duplicate-argument suppression. ac_configure_args= ac_configure_args0= ac_configure_args1= ac_must_keep_next=false for ac_pass in 1 2 do for ac_arg do case $ac_arg in -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) continue ;; *\'*) ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; esac case $ac_pass in 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;; 2) as_fn_append ac_configure_args1 " '$ac_arg'" if test $ac_must_keep_next = true; then ac_must_keep_next=false # Got value, back to normal. else case $ac_arg in *=* | --config-cache | -C | -disable-* | --disable-* \ | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ | -with-* | --with-* | -without-* | --without-* | --x) case "$ac_configure_args0 " in "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; esac ;; -* ) ac_must_keep_next=true ;; esac fi as_fn_append ac_configure_args " '$ac_arg'" ;; esac done done { ac_configure_args0=; unset ac_configure_args0;} { ac_configure_args1=; unset ac_configure_args1;} # When interrupted or exit'd, cleanup temporary files, and complete # config.log. We remove comments because anyway the quotes in there # would cause problems or look ugly. # WARNING: Use '\'' to represent an apostrophe within the trap. # WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug. trap 'exit_status=$? # Save into config.log some information that might help in debugging. { echo $as_echo "## ---------------- ## ## Cache variables. ## ## ---------------- ##" echo # The following way of writing the cache mishandles newlines in values, ( for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #( *${as_nl}ac_space=\ *) sed -n \ "s/'\''/'\''\\\\'\'''\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p" ;; #( *) sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) echo $as_echo "## ----------------- ## ## Output variables. ## ## ----------------- ##" echo for ac_var in $ac_subst_vars do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo if test -n "$ac_subst_files"; then $as_echo "## ------------------- ## ## File substitutions. ## ## ------------------- ##" echo for ac_var in $ac_subst_files do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo fi if test -s confdefs.h; then $as_echo "## ----------- ## ## confdefs.h. ## ## ----------- ##" echo cat confdefs.h echo fi test "$ac_signal" != 0 && $as_echo "$as_me: caught signal $ac_signal" $as_echo "$as_me: exit $exit_status" } >&5 rm -f core *.core core.conftest.* && rm -f -r conftest* confdefs* conf$$* $ac_clean_files && exit $exit_status ' 0 for ac_signal in 1 2 13 15; do trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal done ac_signal=0 # confdefs.h avoids OS command line length limits that DEFS can exceed. rm -f -r conftest* confdefs.h $as_echo "/* confdefs.h */" > confdefs.h # Predefined preprocessor variables. cat >>confdefs.h <<_ACEOF #define PACKAGE_NAME "$PACKAGE_NAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_TARNAME "$PACKAGE_TARNAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_VERSION "$PACKAGE_VERSION" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_STRING "$PACKAGE_STRING" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_URL "$PACKAGE_URL" _ACEOF # Let the site file select an alternate cache file if it wants to. # Prefer an explicitly selected file to automatically selected ones. ac_site_file1=NONE ac_site_file2=NONE if test -n "$CONFIG_SITE"; then # We do not want a PATH search for config.site. case $CONFIG_SITE in #(( -*) ac_site_file1=./$CONFIG_SITE;; */*) ac_site_file1=$CONFIG_SITE;; *) ac_site_file1=./$CONFIG_SITE;; esac elif test "x$prefix" != xNONE; then ac_site_file1=$prefix/share/config.site ac_site_file2=$prefix/etc/config.site else ac_site_file1=$ac_default_prefix/share/config.site ac_site_file2=$ac_default_prefix/etc/config.site fi for ac_site_file in "$ac_site_file1" "$ac_site_file2" do test "x$ac_site_file" = xNONE && continue if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5 $as_echo "$as_me: loading site script $ac_site_file" >&6;} sed 's/^/| /' "$ac_site_file" >&5 . "$ac_site_file" \ || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "failed to load site script $ac_site_file See \`config.log' for more details" "$LINENO" 5; } fi done if test -r "$cache_file"; then # Some versions of bash will fail to source /dev/null (special files # actually), so we avoid doing that. DJGPP emulates it as a regular file. if test /dev/null != "$cache_file" && test -f "$cache_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5 $as_echo "$as_me: loading cache $cache_file" >&6;} case $cache_file in [\\/]* | ?:[\\/]* ) . "$cache_file";; *) . "./$cache_file";; esac fi else { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5 $as_echo "$as_me: creating cache $cache_file" >&6;} >$cache_file fi # Check that the precious variables saved in the cache have kept the same # value. ac_cache_corrupted=false for ac_var in $ac_precious_vars; do eval ac_old_set=\$ac_cv_env_${ac_var}_set eval ac_new_set=\$ac_env_${ac_var}_set eval ac_old_val=\$ac_cv_env_${ac_var}_value eval ac_new_val=\$ac_env_${ac_var}_value case $ac_old_set,$ac_new_set in set,) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} ac_cache_corrupted=: ;; ,set) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} ac_cache_corrupted=: ;; ,);; *) if test "x$ac_old_val" != "x$ac_new_val"; then # differences in whitespace do not lead to failure. ac_old_val_w=`echo x $ac_old_val` ac_new_val_w=`echo x $ac_new_val` if test "$ac_old_val_w" != "$ac_new_val_w"; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5 $as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} ac_cache_corrupted=: else { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5 $as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;} eval $ac_var=\$ac_old_val fi { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5 $as_echo "$as_me: former value: \`$ac_old_val'" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5 $as_echo "$as_me: current value: \`$ac_new_val'" >&2;} fi;; esac # Pass precious variables to config.status. if test "$ac_new_set" = set; then case $ac_new_val in *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; *) ac_arg=$ac_var=$ac_new_val ;; esac case " $ac_configure_args " in *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. *) as_fn_append ac_configure_args " '$ac_arg'" ;; esac fi done if $ac_cache_corrupted; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5 $as_echo "$as_me: error: changes in the environment can compromise the build" >&2;} as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5 fi ## -------------------- ## ## Main body of script. ## ## -------------------- ## ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu # Check for Ocaml compilers # we first look for ocamlc in the path; if not present, we abort # Extract the first word of "ocamlc", so it can be a program name with args. set dummy ocamlc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OCAMLC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OCAMLC"; then ac_cv_prog_OCAMLC="$OCAMLC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OCAMLC="ocamlc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_OCAMLC" && ac_cv_prog_OCAMLC="no" fi fi OCAMLC=$ac_cv_prog_OCAMLC if test -n "$OCAMLC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OCAMLC" >&5 $as_echo "$OCAMLC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$OCAMLC" = no ; then as_fn_error $? "Cannot find ocamlc." "$LINENO" 5 fi # we extract Ocaml version number and library path OCAMLVERSION=`$OCAMLC -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` echo "ocaml version is $OCAMLVERSION" OCAMLLIB=`$OCAMLC -v | tail -1 | cut -f 4 -d " "` echo "ocaml library path is $OCAMLLIB" # then we look for ocamlopt; if not present, we issue a warning # if the version is not the same, we also discard it # we set OCAMLBEST to "opt" or "byte", whether ocamlopt is available or not # Extract the first word of "ocamlopt", so it can be a program name with args. set dummy ocamlopt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OCAMLOPT+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OCAMLOPT"; then ac_cv_prog_OCAMLOPT="$OCAMLOPT" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OCAMLOPT="ocamlopt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_OCAMLOPT" && ac_cv_prog_OCAMLOPT="no" fi fi OCAMLOPT=$ac_cv_prog_OCAMLOPT if test -n "$OCAMLOPT"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OCAMLOPT" >&5 $as_echo "$OCAMLOPT" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi OCAMLBEST=byte if test "$OCAMLOPT" = no ; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Cannot find ocamlopt; bytecode compilation only." >&5 $as_echo "$as_me: WARNING: Cannot find ocamlopt; bytecode compilation only." >&2;} else { $as_echo "$as_me:${as_lineno-$LINENO}: checking ocamlopt version" >&5 $as_echo_n "checking ocamlopt version... " >&6; } TMPVERSION=`$OCAMLOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVERSION" != $OCAMLVERSION ; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: differs from ocamlc; ocamlopt discarded." >&5 $as_echo "differs from ocamlc; ocamlopt discarded." >&6; } OCAMLOPT=no else { $as_echo "$as_me:${as_lineno-$LINENO}: result: ok" >&5 $as_echo "ok" >&6; } OCAMLBEST=opt fi fi # checking for ocamlc.opt # Extract the first word of "ocamlc.opt", so it can be a program name with args. set dummy ocamlc.opt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OCAMLCDOTOPT+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OCAMLCDOTOPT"; then ac_cv_prog_OCAMLCDOTOPT="$OCAMLCDOTOPT" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OCAMLCDOTOPT="ocamlc.opt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_OCAMLCDOTOPT" && ac_cv_prog_OCAMLCDOTOPT="no" fi fi OCAMLCDOTOPT=$ac_cv_prog_OCAMLCDOTOPT if test -n "$OCAMLCDOTOPT"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OCAMLCDOTOPT" >&5 $as_echo "$OCAMLCDOTOPT" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$OCAMLCDOTOPT" != no ; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking ocamlc.opt version" >&5 $as_echo_n "checking ocamlc.opt version... " >&6; } TMPVERSION=`$OCAMLCDOTOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVERSION" != $OCAMLVERSION ; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: differs from ocamlc; ocamlc.opt discarded." >&5 $as_echo "differs from ocamlc; ocamlc.opt discarded." >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: ok" >&5 $as_echo "ok" >&6; } OCAMLC=$OCAMLCDOTOPT fi fi # checking for ocamlopt.opt if test "$OCAMLOPT" != no ; then # Extract the first word of "ocamlopt.opt", so it can be a program name with args. set dummy ocamlopt.opt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OCAMLOPTDOTOPT+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OCAMLOPTDOTOPT"; then ac_cv_prog_OCAMLOPTDOTOPT="$OCAMLOPTDOTOPT" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OCAMLOPTDOTOPT="ocamlopt.opt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_OCAMLOPTDOTOPT" && ac_cv_prog_OCAMLOPTDOTOPT="no" fi fi OCAMLOPTDOTOPT=$ac_cv_prog_OCAMLOPTDOTOPT if test -n "$OCAMLOPTDOTOPT"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OCAMLOPTDOTOPT" >&5 $as_echo "$OCAMLOPTDOTOPT" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$OCAMLOPTDOTOPT" != no ; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking ocamlc.opt version" >&5 $as_echo_n "checking ocamlc.opt version... " >&6; } TMPVER=`$OCAMLOPTDOTOPT -v | sed -n -e 's|.*version* *\(.*\)$|\1|p' ` if test "$TMPVER" != $OCAMLVERSION ; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: differs from ocamlc; ocamlopt.opt discarded." >&5 $as_echo "differs from ocamlc; ocamlopt.opt discarded." >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: ok" >&5 $as_echo "ok" >&6; } OCAMLOPT=$OCAMLOPTDOTOPT fi fi fi # ocamldep should also be present in the path # Extract the first word of "ocamldep", so it can be a program name with args. set dummy ocamldep; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OCAMLDEP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OCAMLDEP"; then ac_cv_prog_OCAMLDEP="$OCAMLDEP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OCAMLDEP="ocamldep" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_OCAMLDEP" && ac_cv_prog_OCAMLDEP="no" fi fi OCAMLDEP=$ac_cv_prog_OCAMLDEP if test -n "$OCAMLDEP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OCAMLDEP" >&5 $as_echo "$OCAMLDEP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$OCAMLC" = no ; then as_fn_error $? "Cannot find ocamldep." "$LINENO" 5 fi # substitutions to perform # Extract the first word of "mktexlsr", so it can be a program name with args. set dummy mktexlsr; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_MKTEXLSR+:} false; then : $as_echo_n "(cached) " >&6 else case $MKTEXLSR in [\\/]* | ?:[\\/]*) ac_cv_path_MKTEXLSR="$MKTEXLSR" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_MKTEXLSR="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_path_MKTEXLSR" && ac_cv_path_MKTEXLSR="true" ;; esac fi MKTEXLSR=$ac_cv_path_MKTEXLSR if test -n "$MKTEXLSR"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MKTEXLSR" >&5 $as_echo "$MKTEXLSR" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$MKTEXLSR" = true ; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Cannot find mktexlsr." >&5 $as_echo "$as_me: WARNING: Cannot find mktexlsr." >&2;} fi # Finally create all the generated files ac_config_files="$ac_config_files Makefile" cat >confcache <<\_ACEOF # This file is a shell script that caches the results of configure # tests run on this system so they can be shared between configure # scripts and configure runs, see configure's option --config-cache. # It is not useful on other systems. If it contains results you don't # want to keep, you may remove or edit it. # # config.status only pays attention to the cache file if you give it # the --recheck option to rerun configure. # # `ac_cv_env_foo' variables (set or unset) will be overridden when # loading this file, other *unset* `ac_cv_foo' will be assigned the # following values. _ACEOF # The following way of writing the cache mishandles newlines in values, # but we know of no workaround that is simple, portable, and efficient. # So, we kill variables containing newlines. # Ultrix sh set writes to stderr and can't be redirected directly, # and sets the high bit in the cache file unless we assign to the vars. ( for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space=' '; set) 2>&1` in #( *${as_nl}ac_space=\ *) # `set' does not quote correctly, so add quotes: double-quote # substitution turns \\\\ into \\, and sed turns \\ into \. sed -n \ "s/'/'\\\\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" ;; #( *) # `set' quotes correctly as required by POSIX, so do not add quotes. sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) | sed ' /^ac_cv_env_/b end t clear :clear s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/ t end s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ :end' >>confcache if diff "$cache_file" confcache >/dev/null 2>&1; then :; else if test -w "$cache_file"; then if test "x$cache_file" != "x/dev/null"; then { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 $as_echo "$as_me: updating cache $cache_file" >&6;} if test ! -f "$cache_file" || test -h "$cache_file"; then cat confcache >"$cache_file" else case $cache_file in #( */* | ?:*) mv -f confcache "$cache_file"$$ && mv -f "$cache_file"$$ "$cache_file" ;; #( *) mv -f confcache "$cache_file" ;; esac fi fi else { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 $as_echo "$as_me: not updating unwritable cache $cache_file" >&6;} fi fi rm -f confcache test "x$prefix" = xNONE && prefix=$ac_default_prefix # Let make expand exec_prefix. test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' # Transform confdefs.h into DEFS. # Protect against shell expansion while executing Makefile rules. # Protect against Makefile macro expansion. # # If the first sed substitution is executed (which looks for macros that # take arguments), then branch to the quote section. Otherwise, # look for a macro that doesn't take arguments. ac_script=' :mline /\\$/{ N s,\\\n,, b mline } t clear :clear s/^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*([^)]*)\)[ ]*\(.*\)/-D\1=\2/g t quote s/^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)/-D\1=\2/g t quote b any :quote s/[ `~#$^&*(){}\\|;'\''"<>?]/\\&/g s/\[/\\&/g s/\]/\\&/g s/\$/$$/g H :any ${ g s/^\n// s/\n/ /g p } ' DEFS=`sed -n "$ac_script" confdefs.h` ac_libobjs= ac_ltlibobjs= U= for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue # 1. Remove the extension, and $U if already installed. ac_script='s/\$U\././;s/\.o$//;s/\.obj$//' ac_i=`$as_echo "$ac_i" | sed "$ac_script"` # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR # will be set to the directory where LIBOBJS objects are built. as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext" as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo' done LIBOBJS=$ac_libobjs LTLIBOBJS=$ac_ltlibobjs : "${CONFIG_STATUS=./config.status}" ac_write_fail=0 ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files $CONFIG_STATUS" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5 $as_echo "$as_me: creating $CONFIG_STATUS" >&6;} as_write_fail=0 cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1 #! $SHELL # Generated by $as_me. # Run this file to recreate the current configuration. # Compiler output produced by configure, useful for debugging # configure, is in config.log if it exists. debug=false ac_cs_recheck=false ac_cs_silent=false SHELL=\${CONFIG_SHELL-$SHELL} export SHELL _ASEOF cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1 ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" exec 6>&1 ## ----------------------------------- ## ## Main body of $CONFIG_STATUS script. ## ## ----------------------------------- ## _ASEOF test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1 cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Save the log message, to keep $0 and so on meaningful, and to # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" This file was extended by $as_me, which was generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES CONFIG_HEADERS = $CONFIG_HEADERS CONFIG_LINKS = $CONFIG_LINKS CONFIG_COMMANDS = $CONFIG_COMMANDS $ $0 $@ on `(hostname || uname -n) 2>/dev/null | sed 1q` " _ACEOF case $ac_config_files in *" "*) set x $ac_config_files; shift; ac_config_files=$*;; esac cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 # Files that config.status was made for. config_files="$ac_config_files" _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 ac_cs_usage="\ \`$as_me' instantiates files and other configuration actions from templates according to the current configuration. Unless the files and actions are specified as TAGs, all are instantiated by default. Usage: $0 [OPTION]... [TAG]... -h, --help print this help, then exit -V, --version print version number and configuration settings, then exit --config print configuration, then exit -q, --quiet, --silent do not print progress messages -d, --debug don't remove temporary files --recheck update $as_me by reconfiguring in the same conditions --file=FILE[:TEMPLATE] instantiate the configuration file FILE Configuration files: $config_files Report bugs to the package provider." _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ config.status configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" Copyright (C) 2012 Free Software Foundation, Inc. This config.status script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it." ac_pwd='$ac_pwd' srcdir='$srcdir' test -n "\$AWK" || AWK=awk _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # The default lists apply if the user does not specify any file. ac_need_defaults=: while test $# != 0 do case $1 in --*=?*) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'` ac_shift=: ;; --*=) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg= ac_shift=: ;; *) ac_option=$1 ac_optarg=$2 ac_shift=shift ;; esac case $ac_option in # Handling of the options. -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) ac_cs_recheck=: ;; --version | --versio | --versi | --vers | --ver | --ve | --v | -V ) $as_echo "$ac_cs_version"; exit ;; --config | --confi | --conf | --con | --co | --c ) $as_echo "$ac_cs_config"; exit ;; --debug | --debu | --deb | --de | --d | -d ) debug=: ;; --file | --fil | --fi | --f ) $ac_shift case $ac_optarg in *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; '') as_fn_error $? "missing file argument" ;; esac as_fn_append CONFIG_FILES " '$ac_optarg'" ac_need_defaults=false;; --he | --h | --help | --hel | -h ) $as_echo "$ac_cs_usage"; exit ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil | --si | --s) ac_cs_silent=: ;; # This is an error. -*) as_fn_error $? "unrecognized option: \`$1' Try \`$0 --help' for more information." ;; *) as_fn_append ac_config_targets " $1" ac_need_defaults=false ;; esac shift done ac_configure_extra_args= if $ac_cs_silent; then exec 6>/dev/null ac_configure_extra_args="$ac_configure_extra_args --silent" fi _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 if \$ac_cs_recheck; then set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion shift \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6 CONFIG_SHELL='$SHELL' export CONFIG_SHELL exec "\$@" fi _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 exec 5>>config.log { echo sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX ## Running $as_me. ## _ASBOX $as_echo "$ac_log" } >&5 _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Handling of arguments. for ac_config_target in $ac_config_targets do case $ac_config_target in "Makefile") CONFIG_FILES="$CONFIG_FILES Makefile" ;; *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; esac done # If the user did not use the arguments to specify the items to instantiate, # then the envvar interface is used. Set only those that are not. # We use the long form for the default assignment because of an extremely # bizarre bug on SunOS 4.1.3. if $ac_need_defaults; then test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files fi # Have a temporary directory for convenience. Make it in the build tree # simply because there is no reason against having it here, and in addition, # creating and moving files from /tmp can sometimes cause problems. # Hook for its removal unless debugging. # Note that there is a small window in which the directory will not be cleaned: # after its creation but before its name has been assigned to `$tmp'. $debug || { tmp= ac_tmp= trap 'exit_status=$? : "${ac_tmp:=$tmp}" { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status ' 0 trap 'as_fn_exit 1' 1 2 13 15 } # Create a (secure) tmp directory for tmp files. { tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && test -d "$tmp" } || { tmp=./conf$$-$RANDOM (umask 077 && mkdir "$tmp") } || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 ac_tmp=$tmp # Set up the scripts for CONFIG_FILES section. # No need to generate them if there are no CONFIG_FILES. # This happens for instance with `./config.status config.h'. if test -n "$CONFIG_FILES"; then ac_cr=`echo X | tr X '\015'` # On cygwin, bash can eat \r inside `` if the user requested igncr. # But we know of no other shell where ac_cr would be empty at this # point, so we can use a bashism as a fallback. if test "x$ac_cr" = x; then eval ac_cr=\$\'\\r\' fi ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' /dev/null` if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then ac_cs_awk_cr='\\r' else ac_cs_awk_cr=$ac_cr fi echo 'BEGIN {' >"$ac_tmp/subs1.awk" && _ACEOF { echo "cat >conf$$subs.awk <<_ACEOF" && echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' && echo "_ACEOF" } >conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'` ac_delim='%!_!# ' for ac_last_try in false false false false false :; do . ./conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X` if test $ac_delim_n = $ac_delim_num; then break elif $ac_last_try; then as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 else ac_delim="$ac_delim!$ac_delim _$ac_delim!! " fi done rm -f conf$$subs.sh cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && _ACEOF sed -n ' h s/^/S["/; s/!.*/"]=/ p g s/^[^!]*!// :repl t repl s/'"$ac_delim"'$// t delim :nl h s/\(.\{148\}\)..*/\1/ t more1 s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/ p n b repl :more1 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t nl :delim h s/\(.\{148\}\)..*/\1/ t more2 s/["\\]/\\&/g; s/^/"/; s/$/"/ p b :more2 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t delim ' >$CONFIG_STATUS || ac_write_fail=1 rm -f conf$$subs.awk cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACAWK cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && for (key in S) S_is_set[key] = 1 FS = "" } { line = $ 0 nfields = split(line, field, "@") substed = 0 len = length(field[1]) for (i = 2; i < nfields; i++) { key = field[i] keylen = length(key) if (S_is_set[key]) { value = S[key] line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3) len += length(value) + length(field[++i]) substed = 1 } else len += 1 + keylen } print line } _ACAWK _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" else cat fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 _ACEOF # VPATH may cause trouble with some makes, so we remove sole $(srcdir), # ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and # trailing colons and then remove the whole line if VPATH becomes empty # (actually we leave an empty line to preserve line numbers). if test "x$srcdir" = x.; then ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{ h s/// s/^/:/ s/[ ]*$/:/ s/:\$(srcdir):/:/g s/:\${srcdir}:/:/g s/:@srcdir@:/:/g s/^:*// s/:*$// x s/\(=[ ]*\).*/\1/ G s/\n// s/^[^=]*=[ ]*$// }' fi cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 fi # test -n "$CONFIG_FILES" eval set X " :F $CONFIG_FILES " shift for ac_tag do case $ac_tag in :[FHLC]) ac_mode=$ac_tag; continue;; esac case $ac_mode$ac_tag in :[FHL]*:*);; :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; :[FH]-) ac_tag=-:-;; :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; esac ac_save_IFS=$IFS IFS=: set x $ac_tag IFS=$ac_save_IFS shift ac_file=$1 shift case $ac_mode in :L) ac_source=$1;; :[FH]) ac_file_inputs= for ac_f do case $ac_f in -) ac_f="$ac_tmp/stdin";; *) # Look for the file first in the build tree, then in the source tree # (if the path is not absolute). The absolute path cannot be DOS-style, # because $ac_f cannot contain `:'. test -f "$ac_f" || case $ac_f in [\\/$]*) false;; *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; esac || as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; esac case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac as_fn_append ac_file_inputs " '$ac_f'" done # Let's still pretend it is `configure' which instantiates (i.e., don't # use $as_me), people would be surprised to read: # /* config.h. Generated by config.status. */ configure_input='Generated from '` $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g' `' by configure.' if test x"$ac_file" != x-; then configure_input="$ac_file. $configure_input" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5 $as_echo "$as_me: creating $ac_file" >&6;} fi # Neutralize special characters interpreted by sed in replacement strings. case $configure_input in #( *\&* | *\|* | *\\* ) ac_sed_conf_input=`$as_echo "$configure_input" | sed 's/[\\\\&|]/\\\\&/g'`;; #( *) ac_sed_conf_input=$configure_input;; esac case $ac_tag in *:-:* | *:-) cat >"$ac_tmp/stdin" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac ;; esac ac_dir=`$as_dirname -- "$ac_file" || $as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$ac_file" : 'X\(//\)[^/]' \| \ X"$ac_file" : 'X\(//\)$' \| \ X"$ac_file" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$ac_file" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` as_dir="$ac_dir"; as_fn_mkdir_p ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix case $ac_mode in :F) # # CONFIG_FILE # _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # If the template does not know about datarootdir, expand it. # FIXME: This hack should be removed a few years after 2.60. ac_datarootdir_hack=; ac_datarootdir_seen= ac_sed_dataroot=' /datarootdir/ { p q } /@datadir@/p /@docdir@/p /@infodir@/p /@localedir@/p /@mandir@/p' case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in *datarootdir*) ac_datarootdir_seen=yes;; *@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5 $as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;} _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_datarootdir_hack=' s&@datadir@&$datadir&g s&@docdir@&$docdir&g s&@infodir@&$infodir&g s&@localedir@&$localedir&g s&@mandir@&$mandir&g s&\\\${datarootdir}&$datarootdir&g' ;; esac _ACEOF # Neutralize VPATH when `$srcdir' = `.'. # Shell code in configure.ac might set extrasub. # FIXME: do we really want to maintain this feature? cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_sed_extra="$ac_vpsub $extrasub _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 :t /@[a-zA-Z_][a-zA-Z_0-9]*@/!b s|@configure_input@|$ac_sed_conf_input|;t t s&@top_builddir@&$ac_top_builddir_sub&;t t s&@top_build_prefix@&$ac_top_build_prefix&;t t s&@srcdir@&$ac_srcdir&;t t s&@abs_srcdir@&$ac_abs_srcdir&;t t s&@top_srcdir@&$ac_top_srcdir&;t t s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t s&@builddir@&$ac_builddir&;t t s&@abs_builddir@&$ac_abs_builddir&;t t s&@abs_top_builddir@&$ac_abs_top_builddir&;t t $ac_datarootdir_hack " eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ "$ac_tmp/out"`; test -z "$ac_out"; } && { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&5 $as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&2;} rm -f "$ac_tmp/stdin" case $ac_file in -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; esac \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac done # for ac_tag as_fn_exit 0 _ACEOF ac_clean_files=$ac_clean_files_save test $ac_write_fail = 0 || as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5 # configure is writing to config.log, and then calls config.status. # config.status does its own redirection, appending to config.log. # Unfortunately, on DOS this fails, as config.log is still kept open # by configure, so config.status won't be able to write to it; its # output is simply discarded. So we exec the FD to /dev/null, # effectively closing config.log, so it can be properly (re)opened and # appended to by config.status. When coming back to configure, we # need to make the FD available again. if test "$no_create" != yes; then ac_cs_success=: ac_config_status_args= test "$silent" = yes && ac_config_status_args="$ac_config_status_args --quiet" exec 5>/dev/null $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false exec 5>>config.log # Use ||, not &&, to avoid exiting from the if with $? = 1, which # would make configure fail if this is the last instruction. $ac_cs_success || as_fn_exit 1 fi if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5 $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;} fi chmod a-w Makefile ocamlweb-1.41/.depend0000644000246300004300000001132113422556306014025 0ustar filliatrvalsdoclexer.cmi: web.cmi yacc_parser.cmi: yacc_syntax.cmi yacc_syntax.cmi: ocamllex-parser/lex_syntax.cmi cross.cmo: yacc_syntax.cmi yacc_parser.cmi yacc_lexer.cmo \ ocaml-parser/syntaxerr.cmi ocaml-parser/parsetree.cmi \ ocaml-parser/parse.cmi output.cmi ocaml-parser/longident.cmi \ ocaml-parser/location.cmi ocaml-parser/lexer.cmi \ ocamllex-parser/lex_syntax.cmi ocamllex-parser/lex_parser.cmi \ ocamllex-parser/lex_lexer.cmo ocaml-parser/asttypes.cmi cross.cmi cross.cmx: yacc_syntax.cmx yacc_parser.cmx yacc_lexer.cmx \ ocaml-parser/syntaxerr.cmx ocaml-parser/parsetree.cmi \ ocaml-parser/parse.cmx output.cmx ocaml-parser/longident.cmx \ ocaml-parser/location.cmx ocaml-parser/lexer.cmx \ ocamllex-parser/lex_syntax.cmi ocamllex-parser/lex_parser.cmx \ ocamllex-parser/lex_lexer.cmx ocaml-parser/asttypes.cmi cross.cmi doclexer.cmo: web.cmi pretty.cmi output.cmi doclexer.cmi doclexer.cmx: web.cmx pretty.cmx output.cmx doclexer.cmi main.cmo: web.cmi version.cmo output.cmi doclexer.cmi main.cmx: web.cmx version.cmx output.cmx doclexer.cmx output.cmo: output.cmi output.cmx: output.cmi pretty.cmo: output.cmi pretty.cmi pretty.cmx: output.cmx pretty.cmi web.cmo: pretty.cmi output.cmi cross.cmi web.cmi web.cmx: pretty.cmx output.cmx cross.cmx web.cmi yacc_lexer.cmo: yacc_syntax.cmi yacc_parser.cmi \ ocamllex-parser/lex_syntax.cmi yacc_lexer.cmx: yacc_syntax.cmx yacc_parser.cmx \ ocamllex-parser/lex_syntax.cmi yacc_parser.cmo: yacc_syntax.cmi ocamllex-parser/lex_syntax.cmi \ yacc_parser.cmi yacc_parser.cmx: yacc_syntax.cmx ocamllex-parser/lex_syntax.cmi \ yacc_parser.cmi yacc_syntax.cmo: output.cmi ocamllex-parser/lex_syntax.cmi yacc_syntax.cmi yacc_syntax.cmx: output.cmx ocamllex-parser/lex_syntax.cmi yacc_syntax.cmi ocaml-parser/lexer.cmo: ocaml-parser/warnings.cmi ocaml-parser/parser.cmi \ ocaml-parser/misc.cmi ocaml-parser/location.cmi ocaml-parser/lexer.cmi ocaml-parser/lexer.cmx: ocaml-parser/warnings.cmx ocaml-parser/parser.cmx \ ocaml-parser/misc.cmx ocaml-parser/location.cmx ocaml-parser/lexer.cmi ocaml-parser/linenum.cmo: ocaml-parser/misc.cmi ocaml-parser/linenum.cmi ocaml-parser/linenum.cmx: ocaml-parser/misc.cmx ocaml-parser/linenum.cmi ocaml-parser/location.cmo: ocaml-parser/warnings.cmi \ ocaml-parser/terminfo.cmi ocaml-parser/linenum.cmi \ ocaml-parser/location.cmi ocaml-parser/location.cmx: ocaml-parser/warnings.cmx \ ocaml-parser/terminfo.cmx ocaml-parser/linenum.cmx \ ocaml-parser/location.cmi ocaml-parser/longident.cmo: ocaml-parser/misc.cmi ocaml-parser/longident.cmi ocaml-parser/longident.cmx: ocaml-parser/misc.cmx ocaml-parser/longident.cmi ocaml-parser/misc.cmo: ocaml-parser/misc.cmi ocaml-parser/misc.cmx: ocaml-parser/misc.cmi ocaml-parser/parse.cmo: ocaml-parser/syntaxerr.cmi ocaml-parser/parser.cmi \ ocaml-parser/location.cmi ocaml-parser/lexer.cmi ocaml-parser/parse.cmi ocaml-parser/parse.cmx: ocaml-parser/syntaxerr.cmx ocaml-parser/parser.cmx \ ocaml-parser/location.cmx ocaml-parser/lexer.cmx ocaml-parser/parse.cmi ocaml-parser/parser.cmo: ocaml-parser/syntaxerr.cmi \ ocaml-parser/parsetree.cmi ocaml-parser/longident.cmi \ ocaml-parser/location.cmi ocaml-parser/clflags.cmo \ ocaml-parser/asttypes.cmi ocaml-parser/parser.cmi ocaml-parser/parser.cmx: ocaml-parser/syntaxerr.cmx \ ocaml-parser/parsetree.cmi ocaml-parser/longident.cmx \ ocaml-parser/location.cmx ocaml-parser/clflags.cmx \ ocaml-parser/asttypes.cmi ocaml-parser/parser.cmi ocaml-parser/syntaxerr.cmo: ocaml-parser/location.cmi \ ocaml-parser/syntaxerr.cmi ocaml-parser/syntaxerr.cmx: ocaml-parser/location.cmx \ ocaml-parser/syntaxerr.cmi ocaml-parser/terminfo.cmo: ocaml-parser/terminfo.cmi ocaml-parser/terminfo.cmx: ocaml-parser/terminfo.cmi ocaml-parser/warnings.cmo: ocaml-parser/warnings.cmi ocaml-parser/warnings.cmx: ocaml-parser/warnings.cmi ocaml-parser/lexer.cmi: ocaml-parser/parser.cmi ocaml-parser/location.cmi ocaml-parser/location.cmi: ocaml-parser/warnings.cmi ocaml-parser/parse.cmi: ocaml-parser/parsetree.cmi ocaml-parser/parser.cmi: ocaml-parser/parsetree.cmi ocaml-parser/parsetree.cmi: ocaml-parser/longident.cmi \ ocaml-parser/location.cmi ocaml-parser/asttypes.cmi ocaml-parser/syntaxerr.cmi: ocaml-parser/location.cmi ocamllex-parser/lex_lexer.cmo: ocamllex-parser/lex_syntax.cmi \ ocamllex-parser/lex_parser.cmi ocamllex-parser/lex_lexer.cmx: ocamllex-parser/lex_syntax.cmi \ ocamllex-parser/lex_parser.cmx ocamllex-parser/lex_parser.cmo: ocamllex-parser/lex_syntax.cmi \ ocamllex-parser/lex_parser.cmi ocamllex-parser/lex_parser.cmx: ocamllex-parser/lex_syntax.cmi \ ocamllex-parser/lex_parser.cmi ocamllex-parser/lex_parser.cmi: ocamllex-parser/lex_syntax.cmi ocamlweb-1.41/README0000644000246300004300000000100213422556306013440 0ustar filliatrvalsocamlweb is a literate programming tool for Objective Caml The invocation is ocamlweb It creates a single LaTeX document with both documentation and code (implementations and interfaces) extracted from the given files. Documentation is inserted into ocaml files as comments and thus your files will ever compile, no matter the fact you use ocamlweb or not. See the manual for options. COPYRIGHT ========= This program is distributed under the GNU LGPL. See the enclosed file COPYING. ocamlweb-1.41/INSTALL0000644000246300004300000000372513422556306013627 0ustar filliatrvals COMPILATION / INSTALLATION (source distribution) ================================================ You need Objective Caml (>= 2.01) to compile the sources. 1. Use configure script by typing "./configure" Default target directories are BINDIR = /usr/local/bin TEXDIR = /usr/share/texmf/tex/latex/misc You can change these values using the --prefix option of configure (see ./configure --help) 2. Compile with "make". It creates a binary file "ocamlweb". 3. Install with "make install" Note: For some TeX installations, it may be necessary to run the command "mktexlsr" by hand to make ocamlweb.sty accessible by LaTeX. Alternatively, you may copy the needed files by hand: copy the binary file "ocamlweb" in some directory that exists in your PATH environment variable, and copy the file "ocamlweb.sty" somewhere in your LaTeX input path (one of the directories listed in $TEXINPUTS). This file is needed to compile the documents produced by ocamlweb with LaTeX. 4. (Optional) You can run "make check" to `bootstrap' ocamlweb i.e. to apply it to its own code. If everything works fine, it will create a DVI document test/ocamlweb.dvi. 5. Clean the sources with "make clean" INSTALLATION (binary distribution) ================================== copy the binary file "ocamlweb" in some directory that exists in your PATH environment variable, and copy the file "ocamlweb.sty" somewhere in your LaTeX input path (one of the directories listed in $TEXINPUTS). This file is needed to compile the documents produced by ocamlweb with LaTeX. NOTE TO THE TexLive USERS ========================= The LaTeX document produced by ocamlweb uses the 'fullpage' package (to get margins adapted to A4 paper). This package has been rewritten in the TeXLive and may cause bad DVI or PostScript (superposed texts). If so, please get the standard FULLPAGE.STY by H.Partl from http://www.ctan.org/. ocamlweb-1.41/COPYING0000755000246300004300000000211613422556306013625 0ustar filliatrvalsocamlweb - a literate programming tool for Objective Caml Copyright (C) 1999-2001 Jean-Christophe FILLIÂTRE and Claude MARCHÉ contributions by Patrick LOISELEUR, Pierre COURTIEU, François POTTIER, Christian RINDERKNECHT, Anne DORLAND and Guillaume MULLER (help for lex/yacc support) Ralf Treinen (debian package) This program is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License version 2, as published by the Free Software Foundation. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License version 2 for more details (enclosed in the file LGPL). ====================================================================== All files in the directory ocaml-parser are Copyright (C) 1996 "Institut National de Recherche en Informatique et en Automatique" and distributed under the terms of the Q Public License version 1.0 See the file ocaml-parser/LICENSE. ocamlweb-1.41/LGPL0000644000246300004300000006127313422556306013261 0ustar filliatrvals GNU LIBRARY GENERAL PUBLIC LICENSE Version 2, June 1991 Copyright (C) 1991 Free Software Foundation, Inc. 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. [This is the first released version of the library GPL. It is numbered 2 because it goes with version 2 of the ordinary GPL.] Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public Licenses are intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This license, the Library General Public License, applies to some specially designated Free Software Foundation software, and to any other libraries whose authors decide to use it. You can use it for your libraries, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for this service if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs; and that you know you can do these things. To protect your rights, we need to make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights. These restrictions translate to certain responsibilities for you if you distribute copies of the library, or if you modify it. For example, if you distribute copies of the library, whether gratis or for a fee, you must give the recipients all the rights that we gave you. You must make sure that they, too, receive or can get the source code. If you link a program with the library, you must provide complete object files to the recipients so that they can relink them with the library, after making changes to the library and recompiling it. And you must show them these terms so they know their rights. Our method of protecting your rights has two steps: (1) copyright the library, and (2) offer you this license which gives you legal permission to copy, distribute and/or modify the library. Also, for each distributor's protection, we want to make certain that everyone understands that there is no warranty for this free library. If the library is modified by someone else and passed on, we want its recipients to know that what they have is not the original version, so that any problems introduced by others will not reflect on the original authors' reputations. Finally, any free program is threatened constantly by software patents. We wish to avoid the danger that companies distributing free software will individually obtain patent licenses, thus in effect transforming the program into proprietary software. To prevent this, we have made it clear that any patent must be licensed for everyone's free use or not licensed at all. Most GNU software, including some libraries, is covered by the ordinary GNU General Public License, which was designed for utility programs. This license, the GNU Library General Public License, applies to certain designated libraries. This license is quite different from the ordinary one; be sure to read it in full, and don't assume that anything in it is the same as in the ordinary license. The reason we have a separate public license for some libraries is that they blur the distinction we usually make between modifying or adding to a program and simply using it. Linking a program with a library, without changing the library, is in some sense simply using the library, and is analogous to running a utility program or application program. However, in a textual and legal sense, the linked executable is a combined work, a derivative of the original library, and the ordinary General Public License treats it as such. Because of this blurred distinction, using the ordinary General Public License for libraries did not effectively promote software sharing, because most developers did not use the libraries. We concluded that weaker conditions might promote sharing better. However, unrestricted linking of non-free programs would deprive the users of those programs of all benefit from the free status of the libraries themselves. This Library General Public License is intended to permit developers of non-free programs to use free libraries, while preserving your freedom as a user of such programs to change the free libraries that are incorporated in them. (We have not seen how to achieve this as regards changes in header files, but we have achieved it as regards changes in the actual functions of the Library.) The hope is that this will lead to faster development of free libraries. The precise terms and conditions for copying, distribution and modification follow. Pay close attention to the difference between a "work based on the library" and a "work that uses the library". The former contains code derived from the library, while the latter only works together with the library. Note that it is possible for a library to be covered by the ordinary General Public License rather than by this special one. GNU LIBRARY GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License Agreement applies to any software library which contains a notice placed by the copyright holder or other authorized party saying it may be distributed under the terms of this Library General Public License (also called "this License"). Each licensee is addressed as "you". A "library" means a collection of software functions and/or data prepared so as to be conveniently linked with application programs (which use some of those functions and data) to form executables. The "Library", below, refers to any such software library or work which has been distributed under these terms. A "work based on the Library" means either the Library or any derivative work under copyright law: that is to say, a work containing the Library or a portion of it, either verbatim or with modifications and/or translated straightforwardly into another language. (Hereinafter, translation is included without limitation in the term "modification".) "Source code" for a work means the preferred form of the work for making modifications to it. For a library, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the library. Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running a program using the Library is not restricted, and output from such a program is covered only if its contents constitute a work based on the Library (independent of the use of the Library in a tool for writing it). Whether that is true depends on what the Library does and what the program that uses the Library does. 1. You may copy and distribute verbatim copies of the Library's complete source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and distribute a copy of this License along with the Library. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Library or any portion of it, thus forming a work based on the Library, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) The modified work must itself be a software library. b) You must cause the files modified to carry prominent notices stating that you changed the files and the date of any change. c) You must cause the whole of the work to be licensed at no charge to all third parties under the terms of this License. d) If a facility in the modified Library refers to a function or a table of data to be supplied by an application program that uses the facility, other than as an argument passed when the facility is invoked, then you must make a good faith effort to ensure that, in the event an application does not supply such function or table, the facility still operates, and performs whatever part of its purpose remains meaningful. (For example, a function in a library to compute square roots has a purpose that is entirely well-defined independent of the application. Therefore, Subsection 2d requires that any application-supplied function or table used by this function must be optional: if the application does not supply it, the square root function must still compute square roots.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Library, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Library, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Library. In addition, mere aggregation of another work not based on the Library with the Library (or with a work based on the Library) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may opt to apply the terms of the ordinary GNU General Public License instead of this License to a given copy of the Library. To do this, you must alter all the notices that refer to this License, so that they refer to the ordinary GNU General Public License, version 2, instead of to this License. (If a newer version than version 2 of the ordinary GNU General Public License has appeared, then you can specify that version instead if you wish.) Do not make any other change in these notices. Once this change is made in a given copy, it is irreversible for that copy, so the ordinary GNU General Public License applies to all subsequent copies and derivative works made from that copy. This option is useful when you wish to copy part of the code of the Library into a program that is not a library. 4. You may copy and distribute the Library (or a portion or derivative of it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange. If distribution of object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place satisfies the requirement to distribute the source code, even though third parties are not compelled to copy the source along with the object code. 5. A program that contains no derivative of any portion of the Library, but is designed to work with the Library by being compiled or linked with it, is called a "work that uses the Library". Such a work, in isolation, is not a derivative work of the Library, and therefore falls outside the scope of this License. However, linking a "work that uses the Library" with the Library creates an executable that is a derivative of the Library (because it contains portions of the Library), rather than a "work that uses the library". The executable is therefore covered by this License. Section 6 states terms for distribution of such executables. When a "work that uses the Library" uses material from a header file that is part of the Library, the object code for the work may be a derivative work of the Library even though the source code is not. Whether this is true is especially significant if the work can be linked without the Library, or if the work is itself a library. The threshold for this to be true is not precisely defined by law. If such an object file uses only numerical parameters, data structure layouts and accessors, and small macros and small inline functions (ten lines or less in length), then the use of the object file is unrestricted, regardless of whether it is legally a derivative work. (Executables containing this object code plus portions of the Library will still fall under Section 6.) Otherwise, if the work is a derivative of the Library, you may distribute the object code for the work under the terms of Section 6. Any executables containing that work also fall under Section 6, whether or not they are linked directly with the Library itself. 6. As an exception to the Sections above, you may also compile or link a "work that uses the Library" with the Library to produce a work containing portions of the Library, and distribute that work under terms of your choice, provided that the terms permit modification of the work for the customer's own use and reverse engineering for debugging such modifications. You must give prominent notice with each copy of the work that the Library is used in it and that the Library and its use are covered by this License. You must supply a copy of this License. If the work during execution displays copyright notices, you must include the copyright notice for the Library among them, as well as a reference directing the user to the copy of this License. Also, you must do one of these things: a) Accompany the work with the complete corresponding machine-readable source code for the Library including whatever changes were used in the work (which must be distributed under Sections 1 and 2 above); and, if the work is an executable linked with the Library, with the complete machine-readable "work that uses the Library", as object code and/or source code, so that the user can modify the Library and then relink to produce a modified executable containing the modified Library. (It is understood that the user who changes the contents of definitions files in the Library will not necessarily be able to recompile the application to use the modified definitions.) b) Accompany the work with a written offer, valid for at least three years, to give the same user the materials specified in Subsection 6a, above, for a charge no more than the cost of performing this distribution. c) If distribution of the work is made by offering access to copy from a designated place, offer equivalent access to copy the above specified materials from the same place. d) Verify that the user has already received a copy of these materials or that you have already sent this user a copy. For an executable, the required form of the "work that uses the Library" must include any data and utility programs needed for reproducing the executable from it. However, as a special exception, the source code distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. It may happen that this requirement contradicts the license restrictions of other proprietary libraries that do not normally accompany the operating system. Such a contradiction means you cannot use both them and the Library together in an executable that you distribute. 7. You may place library facilities that are a work based on the Library side-by-side in a single library together with other library facilities not covered by this License, and distribute such a combined library, provided that the separate distribution of the work based on the Library and of the other library facilities is otherwise permitted, and provided that you do these two things: a) Accompany the combined library with a copy of the same work based on the Library, uncombined with any other library facilities. This must be distributed under the terms of the Sections above. b) Give prominent notice with the combined library of the fact that part of it is a work based on the Library, and explaining where to find the accompanying uncombined form of the same work. 8. You may not copy, modify, sublicense, link with, or distribute the Library except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense, link with, or distribute the Library is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 9. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Library or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Library (or any work based on the Library), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Library or works based on it. 10. Each time you redistribute the Library (or any work based on the Library), the recipient automatically receives a license from the original licensor to copy, distribute, link with or modify the Library subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties to this License. 11. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Library at all. For example, if a patent license would not permit royalty-free redistribution of the Library by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Library. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply, and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 12. If the distribution and/or use of the Library is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Library under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 13. The Free Software Foundation may publish revised and/or new versions of the Library General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Library specifies a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Library does not specify a license version number, you may choose any version ever published by the Free Software Foundation. 14. If you wish to incorporate parts of the Library into other free programs whose distribution conditions are incompatible with these, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Libraries If you develop a new library, and you want it to be of the greatest possible use to the public, we recommend making it free software that everyone can redistribute and change. You can do so by permitting redistribution under these terms (or, alternatively, under the terms of the ordinary General Public License). To apply these terms, attach the following notices to the library. It is safest to attach them to the start of each source file to most effectively convey the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; if not, write to the Free Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Also add information on how to contact you by electronic and paper mail. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the library, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the library `Frob' (a library for tweaking knobs) written by James Random Hacker. , 1 April 1990 Ty Coon, President of Vice That's all there is to it! ocamlweb-1.41/CHANGES0000644000246300004300000001641013422556306013564 0ustar filliatrvals(Dis donc emacs, ceci est du -*-text-*- !) LIST OF CHANGES =============== version 1.41, 25/1/2019 ======================= o fixed compilation with OCaml 4.07 (getting rid of terminfo stuff in the OCaml parser, which was not used by ocamlweb anyway) version 1.40, 5/2/2018 ====================== o fixed compilation with recent versions of OCaml o ocamlweb.sty: no more use of macro \tt o default character encoding is now utf8 o new option --encoding to specify a character encoding (e.g. latin1) o new command line option -pdf to output PDF with pdflatex version 1.39, 27/5/2015 ======================= o raw LaTeX with (*l ... *) (patch from Judicaël Courant) version 1.38, 9/5/2012 ====================== o fixed encoding in HTML documentation version 1.37, 4/11/2005 ======================= o fixed bug with page headers (now uses \pagestyle{headings}) version 1.36, 12/10/2004 ======================== o adequacy to ocaml 3.08.1 parser version 1.35, 23/8/2004 ======================= o port to ocaml 3.08 o symbol | now displayed in math mode; no use of package T1 anymore o option --class-options to set the document class options (defaults to `12pt') o fixed cleaning of temporary files when exiting abnormally version 1.34, 7/7/2003 ====================== o fixed behavior on DOS end-of-line version 1.33, 13/5/2003 ======================= o \penalty5000 instead of \nolinebreak in \ocweol (Ralf Treinen) o new macros \ocwbegindcode and \ocwenddcode for code inside documentation version 1.32, 22/1/2003 ======================= o code quotations in titles o comments' indentation now conforms to source files version 1.31, 3/6/2002 ====================== o manuals now contains version number in filenames o \nopagebreak in \ocweol version 1.3, 6/2/2002 ===================== o a warning is issued whenever an ocamlyacc file is correctly parsed by ocamlyacc but is not conformant to ocamlyacc manual (this is about commas and semicolons) o added targets "install-byte" and "dist-clean" in Makefile version 1.2, 14/01/2002 ======================= o single-character identifiers now indexed o port to ocaml 3.04 and adequacy to ocaml 3.04 parser o fixed bugs in ocamlweb.sty (thanks to Ralf Treinen) version 1.1, 20/09/2001 ======================= o fixed bug in module indexing o make LaTeX output the name of the latex file being typeset o better redirections of messages/errors from LaTeX/dvips/hevea o LaTeX messages now displayed (with -dvi,-ps), unless -q o big sections with (*S o nicer pretty-print of [< and >] version 1.0, 15/06/2001 ======================= o option --hevea-option to pass an option to hevea o escaped dollar sign in comments / documentation o fixed bug with yacc token 'error' o adequacy to ocaml 3.01 parser o options -dvi, -ps and -html to produce DVI, PS and HTML directly o page style with headings (thanks to Ralf Treinen) o insertion into LaTeX preamble with option -p and (*p o macros \ocwbegincode and \ocwendcode before and after code pieces (no more use of \codeline and \endcodeline) version 0.9, 18/12/2000 ======================= o support for lex and yacc files (-impl option deprecated on these files) o when not in WEB style, index is by pages by default o noweb style is used if no sectioning command (*s at all so that ocamlweb can be used naively as a pretty-printer o option -latex-sects renamed into -noweb o bytecode compilation if no ocamlopt available o adequacy to ocaml 3.00 parser; labels are now indexed o installation: $(BINDIR) and $(TEXDIR) created if they don't exist o a comment in the LaTeX file now indicates that it is a generated file and gives the command line version 0.8, 02/06/2000 ======================= o configuration with autoconf (thanks to Luc MAZARDO) o location (file + character) in error message for unterminated comments o index entries are now discriminated by their types (value, constructor, type, module, etc.) o nicer quotes in identifiers o pretty-printing of constants (hex, oct and bin integers, floats) o option -s, --short (no titles for files) o pretty-printing for == and != o pretty underscores in identifiers (by redefinition of \_) version 0.7, 31/01/2000 ======================= o support of .mll and .mly files using the --impl option (Christian Rinderknecht); but still no indexing for these files. o fixed bugs in identifiers pretty-printing (Christian Rinderknecht) o fixed bug of code indentation inside item-like environments o renaming of \comment (resp. \endcomment) in \ocwcomment (resp. \ocwendcomment) to avoid a clash with Hevea own macros version 0.6, 21/10/99 ===================== o backtrack on the way to pretty-print comments (comments inside code lines produced line breaks) o many spaces inside code are printed as a single one (so that you can justify in ASCII without an ugly result with LaTeX) o unterminated ocamlweb comments (*i ... *i) now generate an error message version 0.5, 29/9/99 ==================== o better result with hevea (a single line break between code lines, etc.) o escape sequences ([...]) are no more active inside mathematics ($...$) o bootstrap is now completed (make bootstrap) o interfaces are no more inserted automatically before implementations (patch from François Pottier) version 0.4, 25/06/99 ===================== o better handling of spaces before sections (thanks to François Pottier) o right-justified comments with (*r ... *) o misinterpretation of -- in strings fixes o better adequacy to caml tokens (and better pretty-printing) o single letter identifiers are also printed using macros \ocwlowerid, etc. o line breaks in strings are now correctly handled o more single-letter type variables output as greek letters. other type variables output as \ocwtv{id} which is customizable. An additional option --no-greek to ocamlweb disables to use of greek letters. o option -q, --quiet version 0.3, 17/06/99 (first official release) ===================== o \ocwnl has been splitted into \ocweol and \ocwindent for better code printing. a new corresponding function end_line has been added into output.ml. o \verb and \begin{verbatim} correctly handled during pretty-printing o option --no-web becomes --latex-sects o option --no-doc becomes --no-preamble o better sorting and pretty-printing of index entries o fixed bug in global index (interfaces were scanned after implementations when registering locations) o two different macros, \ocwlowerid and \ocwupperid, for capitalized and uncapitalized identifiers o the index now uses LaTeX labels and refs, where all the labels are of the kind \label{filename:location} version 0.26, 02/06/99 ====================== o ocamlweb.sty: greatly improved by Claude Marché o various command line options: --no-index, --no-web, --latex-option, --impl, --intf, --tex o two styles: WEB and LaTeX o ocamlweb now uses the ocaml parser to extract definitions and uses (the modules and classes language is not yet processed) o better adequacy to the ocaml lexer when separating code and documentation version 0.15, 18/5/99 ===================== o first release (only for a few number of users who asked for) $Id$