(* File: make_array.ml

  This "script" will generate "gnuplot_bigarray*.ml" and
   "gnuplot_array.ml" from "gnuplot_generic.ml".  It naive and no more
   general that it needs to be.


   Copyright (C) 2001-2004

     Christophe Troestler
     email: Christophe.Troestler@umh.ac.be
     WWW: http://math.umh.ac.be/an/software/

   This library is free software; you can redistribute it and/or
   modify it under the terms of the GNU Lesser General Public License
   version 2.1 as published by the Free Software Foundation, with the
   special exception on linking described in file LICENSE.

   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 file
   LICENSE for more details.
*)
(* 	$Id: make_array.ml,v 1.4 2004-11-28 23:51:11 chris_77 Exp $	 *)

let arg = "\\([^()]+\\)"

let re_arr = Str.regexp_string "ARRAY"
and re_vec = Str.regexp_string "VEC"
and re_mat = Str.regexp_string "MAT"
and re_lower = Str.regexp_string "LOWER"
and re_upper = Str.regexp ("UPPER *(" ^ arg ^ ")")
and re_get = Str.regexp ("GET *(" ^ arg ^ "," ^ arg ^ ")")
and re_get2 = Str.regexp ("GET2 *(" ^ arg ^ "," ^ arg ^ "," ^ arg ^ ")")

type subst = {
  mod_name : string; (* module name *)
  header : string; (* header of the new file *)
  vec : string;    (* type for vectors -- VEC *)
  mat : string;    (* type for matrices -- MAT *)
  lower : string;  (* lower bound for vectors -- LOWER *)
  upper : string;  (* upper bound for vectors -- UPPER(\1) *)
  get : string;    (* get function -- GET(\1,\2) *)
  get2 : string    (* get function for arrays -- GET2(\1,\2,\3) *)
}


let subtitute infile outfile subst =
  (try Sys.remove outfile with _ -> ()); (* ignore errors *)
  let fh0 = open_in infile in
  let fh1 = open_out outfile in
  Printf.fprintf fh1 "(* Automatically generated from %S. *)\n%s\n"
    infile subst.header;
  try
    while true do
      let l = input_line fh0 in
      let l = Str.global_replace re_arr subst.mod_name l in
      let l = Str.global_replace re_vec subst.vec l in
      let l = Str.global_replace re_mat subst.mat l in
      let l = Str.global_replace re_lower subst.lower l in
      let l = Str.global_replace re_upper subst.upper l in
      let l = Str.global_replace re_get subst.get l in
      let l = Str.global_replace re_get2 subst.get2 l in
      output_string fh1 l;
      output_string fh1 "\n";
    done
  with
    End_of_file -> ();
  close_in fh0;
  close_out fh1;
  Unix.chmod outfile 0o444 (* to prevent accidental modification *)



let () =
  let src_file = "gnuplot_arr_ba.ml" in
  subtitute src_file "gnuplot_array.ml" {
    mod_name = "Array";
    header = "include Gnuplot_common_
type vec = float array
type mat = float array array
";
    vec = "vec";
    mat = "mat";
    lower = "0";
    upper = "Array.length(\\1) - 1";
    get = "Array.unsafe_get(\\1)(\\2)";
    get2 = "Array.unsafe_get (Array.unsafe_get(\\1)(\\2))(\\3)";
  };

  subtitute src_file "gnuplot_ba_c.ml" {
    mod_name = "Bigarray";
    header = "open Gnuplot_common_
open Bigarray";
    vec = "(float, float64_elt, c_layout) Array1.t";
    mat = "(float, float64_elt, c_layout) Array2.t";
    lower = "0";
    upper = "Array1.dim(\\1) - 1";
    get = "\\1.{\\2}";
    get2 = "\\1.{\\2,\\3}";
  };

  subtitute src_file "gnuplot_ba_f.ml" {
    mod_name = "Bigarray";
    header = "open Gnuplot_common_
open Bigarray";
    vec = "(float, float64_elt, fortran_layout) Array1.t";
    mat = "(float, float64_elt, fortran_layout) Array2.t";
    lower = "1";
    upper = "Array1.dim(\\1)";
    get = "\\1.{\\2}";
    get2 = "\\1.{\\2,\\3}";
  }



