Project

General

Profile

Statistics
| Branch: | Tag: | Revision:

lustrec / myocamlbuild.ml @ 22fe1c93

History | View | Annotate | Download (12.7 KB)

1 22fe1c93 ploc
(* OASIS_START *)
2
(* DO NOT EDIT (digest: 7eabc0106cad87d67c960d9a2ff80b28) *)
3
module OASISGettext = struct
4
# 21 "/build/buildd/oasis-0.2.0/src/oasis/OASISGettext.ml"
5
  
6
  let ns_ str = 
7
    str
8
  
9
  let s_ str = 
10
    str
11
  
12
  let f_ (str : ('a, 'b, 'c, 'd) format4) =
13
    str
14
  
15
  let fn_ fmt1 fmt2 n =
16
    if n = 1 then
17
      fmt1^^""
18
    else
19
      fmt2^^""
20
  
21
  let init = 
22
    []
23
  
24
end
25
26
module OASISExpr = struct
27
# 21 "/build/buildd/oasis-0.2.0/src/oasis/OASISExpr.ml"
28
  
29
  
30
  
31
  open OASISGettext
32
  
33
  type test = string 
34
  
35
  type flag = string 
36
  
37
  type t =
38
    | EBool of bool
39
    | ENot of t
40
    | EAnd of t * t
41
    | EOr of t * t
42
    | EFlag of flag
43
    | ETest of test * string
44
    
45
  
46
  type 'a choices = (t * 'a) list 
47
  
48
  let eval var_get t =
49
    let rec eval' = 
50
      function
51
        | EBool b ->
52
            b
53
  
54
        | ENot e -> 
55
            not (eval' e)
56
  
57
        | EAnd (e1, e2) ->
58
            (eval' e1) && (eval' e2)
59
  
60
        | EOr (e1, e2) -> 
61
            (eval' e1) || (eval' e2)
62
  
63
        | EFlag nm ->
64
            let v =
65
              var_get nm
66
            in
67
              assert(v = "true" || v = "false");
68
              (v = "true")
69
  
70
        | ETest (nm, vl) ->
71
            let v =
72
              var_get nm
73
            in
74
              (v = vl)
75
    in
76
      eval' t
77
  
78
  let choose ?printer ?name var_get lst =
79
    let rec choose_aux = 
80
      function
81
        | (cond, vl) :: tl ->
82
            if eval var_get cond then 
83
              vl 
84
            else
85
              choose_aux tl
86
        | [] ->
87
            let str_lst = 
88
              if lst = [] then
89
                s_ "<empty>"
90
              else
91
                String.concat 
92
                  (s_ ", ")
93
                  (List.map
94
                     (fun (cond, vl) ->
95
                        match printer with
96
                          | Some p -> p vl
97
                          | None -> s_ "<no printer>")
98
                     lst)
99
            in
100
              match name with 
101
                | Some nm ->
102
                    failwith
103
                      (Printf.sprintf 
104
                         (f_ "No result for the choice list '%s': %s")
105
                         nm str_lst)
106
                | None ->
107
                    failwith
108
                      (Printf.sprintf
109
                         (f_ "No result for a choice list: %s")
110
                         str_lst)
111
    in
112
      choose_aux (List.rev lst)
113
  
114
end
115
116
117
module BaseEnvLight = struct
118
# 21 "/build/buildd/oasis-0.2.0/src/base/BaseEnvLight.ml"
119
  
120
  module MapString = Map.Make(String)
121
  
122
  type t = string MapString.t
123
  
124
  let default_filename =
125
    Filename.concat 
126
      (Sys.getcwd ())
127
      "setup.data"
128
  
129
  let load ?(allow_empty=false) ?(filename=default_filename) () =
130
    if Sys.file_exists filename then
131
      begin
132
        let chn =
133
          open_in_bin filename
134
        in
135
        let st =
136
          Stream.of_channel chn
137
        in
138
        let line =
139
          ref 1
140
        in
141
        let st_line = 
142
          Stream.from
143
            (fun _ ->
144
               try
145
                 match Stream.next st with 
146
                   | '\n' -> incr line; Some '\n'
147
                   | c -> Some c
148
               with Stream.Failure -> None)
149
        in
150
        let lexer = 
151
          Genlex.make_lexer ["="] st_line
152
        in
153
        let rec read_file mp =
154
          match Stream.npeek 3 lexer with 
155
            | [Genlex.Ident nm; Genlex.Kwd "="; Genlex.String value] ->
156
                Stream.junk lexer; 
157
                Stream.junk lexer; 
158
                Stream.junk lexer;
159
                read_file (MapString.add nm value mp)
160
            | [] ->
161
                mp
162
            | _ ->
163
                failwith
164
                  (Printf.sprintf
165
                     "Malformed data file '%s' line %d"
166
                     filename !line)
167
        in
168
        let mp =
169
          read_file MapString.empty
170
        in
171
          close_in chn;
172
          mp
173
      end
174
    else if allow_empty then
175
      begin
176
        MapString.empty
177
      end
178
    else
179
      begin
180
        failwith 
181
          (Printf.sprintf 
182
             "Unable to load environment, the file '%s' doesn't exist."
183
             filename)
184
      end
185
  
186
  let var_get name env =
187
    let rec var_expand str =
188
      let buff =
189
        Buffer.create ((String.length str) * 2)
190
      in
191
        Buffer.add_substitute 
192
          buff
193
          (fun var -> 
194
             try 
195
               var_expand (MapString.find var env)
196
             with Not_found ->
197
               failwith 
198
                 (Printf.sprintf 
199
                    "No variable %s defined when trying to expand %S."
200
                    var 
201
                    str))
202
          str;
203
        Buffer.contents buff
204
    in
205
      var_expand (MapString.find name env)
206
  
207
  let var_choose lst env = 
208
    OASISExpr.choose
209
      (fun nm -> var_get nm env)
210
      lst
211
end
212
213
214
module MyOCamlbuildFindlib = struct
215
# 21 "/build/buildd/oasis-0.2.0/src/plugins/ocamlbuild/MyOCamlbuildFindlib.ml"
216
  
217
  (** OCamlbuild extension, copied from 
218
    * http://brion.inria.fr/gallium/index.php/Using_ocamlfind_with_ocamlbuild
219
    * by N. Pouillard and others
220
    *
221
    * Updated on 2009/02/28
222
    *
223
    * Modified by Sylvain Le Gall 
224
    *)
225
  open Ocamlbuild_plugin
226
  
227
  (* these functions are not really officially exported *)
228
  let run_and_read = 
229
    Ocamlbuild_pack.My_unix.run_and_read
230
  
231
  let blank_sep_strings = 
232
    Ocamlbuild_pack.Lexers.blank_sep_strings
233
  
234
  let split s ch =
235
    let x = 
236
      ref [] 
237
    in
238
    let rec go s =
239
      let pos = 
240
        String.index s ch 
241
      in
242
        x := (String.before s pos)::!x;
243
        go (String.after s (pos + 1))
244
    in
245
      try
246
        go s
247
      with Not_found -> !x
248
  
249
  let split_nl s = split s '\n'
250
  
251
  let before_space s =
252
    try
253
      String.before s (String.index s ' ')
254
    with Not_found -> s
255
  
256
  (* this lists all supported packages *)
257
  let find_packages () =
258
    List.map before_space (split_nl & run_and_read "ocamlfind list")
259
  
260
  (* this is supposed to list available syntaxes, but I don't know how to do it. *)
261
  let find_syntaxes () = ["camlp4o"; "camlp4r"]
262
  
263
  (* ocamlfind command *)
264
  let ocamlfind x = S[A"ocamlfind"; x]
265
  
266
  let dispatch =
267
    function
268
      | Before_options ->
269
          (* by using Before_options one let command line options have an higher priority *)
270
          (* on the contrary using After_options will guarantee to have the higher priority *)
271
          (* override default commands by ocamlfind ones *)
272
          Options.ocamlc     := ocamlfind & A"ocamlc";
273
          Options.ocamlopt   := ocamlfind & A"ocamlopt";
274
          Options.ocamldep   := ocamlfind & A"ocamldep";
275
          Options.ocamldoc   := ocamlfind & A"ocamldoc";
276
          Options.ocamlmktop := ocamlfind & A"ocamlmktop"
277
                                  
278
      | After_rules ->
279
          
280
          (* When one link an OCaml library/binary/package, one should use -linkpkg *)
281
          flag ["ocaml"; "link"; "program"] & A"-linkpkg";
282
          
283
          (* For each ocamlfind package one inject the -package option when
284
           * compiling, computing dependencies, generating documentation and
285
           * linking. *)
286
          List.iter 
287
            begin fun pkg ->
288
              flag ["ocaml"; "compile";  "pkg_"^pkg] & S[A"-package"; A pkg];
289
              flag ["ocaml"; "ocamldep"; "pkg_"^pkg] & S[A"-package"; A pkg];
290
              flag ["ocaml"; "doc";      "pkg_"^pkg] & S[A"-package"; A pkg];
291
              flag ["ocaml"; "link";     "pkg_"^pkg] & S[A"-package"; A pkg];
292
              flag ["ocaml"; "infer_interface"; "pkg_"^pkg] & S[A"-package"; A pkg];
293
            end 
294
            (find_packages ());
295
  
296
          (* Like -package but for extensions syntax. Morover -syntax is useless
297
           * when linking. *)
298
          List.iter begin fun syntax ->
299
          flag ["ocaml"; "compile";  "syntax_"^syntax] & S[A"-syntax"; A syntax];
300
          flag ["ocaml"; "ocamldep"; "syntax_"^syntax] & S[A"-syntax"; A syntax];
301
          flag ["ocaml"; "doc";      "syntax_"^syntax] & S[A"-syntax"; A syntax];
302
          flag ["ocaml"; "infer_interface"; "syntax_"^syntax] & S[A"-syntax"; A syntax];
303
          end (find_syntaxes ());
304
  
305
          (* The default "thread" tag is not compatible with ocamlfind.
306
           * Indeed, the default rules add the "threads.cma" or "threads.cmxa"
307
           * options when using this tag. When using the "-linkpkg" option with
308
           * ocamlfind, this module will then be added twice on the command line.
309
           *                        
310
           * To solve this, one approach is to add the "-thread" option when using
311
           * the "threads" package using the previous plugin.
312
           *)
313
          flag ["ocaml"; "pkg_threads"; "compile"] (S[A "-thread"]);
314
          flag ["ocaml"; "pkg_threads"; "link"] (S[A "-thread"]);
315
          flag ["ocaml"; "pkg_threads"; "infer_interface"] (S[A "-thread"])
316
  
317
      | _ -> 
318
          ()
319
  
320
end
321
322
module MyOCamlbuildBase = struct
323
# 21 "/build/buildd/oasis-0.2.0/src/plugins/ocamlbuild/MyOCamlbuildBase.ml"
324
  
325
  (** Base functions for writing myocamlbuild.ml
326
      @author Sylvain Le Gall
327
    *)
328
  
329
  
330
  
331
  open Ocamlbuild_plugin
332
  
333
  type dir = string 
334
  type file = string 
335
  type name = string 
336
  type tag = string 
337
  
338
# 55 "/build/buildd/oasis-0.2.0/src/plugins/ocamlbuild/MyOCamlbuildBase.ml"
339
  
340
  type t =
341
      {
342
        lib_ocaml: (name * dir list) list;
343
        lib_c:     (name * dir * file list) list; 
344
        flags:     (tag list * (spec OASISExpr.choices)) list;
345
      } 
346
  
347
  let env_filename =
348
    Pathname.basename 
349
      BaseEnvLight.default_filename
350
  
351
  let dispatch_combine lst =
352
    fun e ->
353
      List.iter 
354
        (fun dispatch -> dispatch e)
355
        lst 
356
  
357
  let dispatch t e = 
358
    let env = 
359
      BaseEnvLight.load 
360
        ~filename:env_filename 
361
        ~allow_empty:true
362
        ()
363
    in
364
      match e with 
365
        | Before_options ->
366
            let no_trailing_dot s =
367
              if String.length s >= 1 && s.[0] = '.' then
368
                String.sub s 1 ((String.length s) - 1)
369
              else
370
                s
371
            in
372
              List.iter
373
                (fun (opt, var) ->
374
                   try 
375
                     opt := no_trailing_dot (BaseEnvLight.var_get var env)
376
                   with Not_found ->
377
                     Printf.eprintf "W: Cannot get variable %s" var)
378
                [
379
                  Options.ext_obj, "ext_obj";
380
                  Options.ext_lib, "ext_lib";
381
                  Options.ext_dll, "ext_dll";
382
                ]
383
  
384
        | After_rules -> 
385
            (* Declare OCaml libraries *)
386
            List.iter 
387
              (function
388
                 | lib, [] ->
389
                     ocaml_lib lib;
390
                 | lib, dir :: tl ->
391
                     ocaml_lib ~dir:dir lib;
392
                     List.iter 
393
                       (fun dir -> 
394
                          flag 
395
                            ["ocaml"; "use_"^lib; "compile"] 
396
                            (S[A"-I"; P dir]))
397
                       tl)
398
              t.lib_ocaml;
399
  
400
            (* Declare C libraries *)
401
            List.iter
402
              (fun (lib, dir, headers) ->
403
                   (* Handle C part of library *)
404
                   flag ["link"; "library"; "ocaml"; "byte"; "use_lib"^lib]
405
                     (S[A"-dllib"; A("-l"^lib); A"-cclib"; A("-l"^lib)]);
406
  
407
                   flag ["link"; "library"; "ocaml"; "native"; "use_lib"^lib]
408
                     (S[A"-cclib"; A("-l"^lib)]);
409
                        
410
                   flag ["link"; "program"; "ocaml"; "byte"; "use_lib"^lib]
411
                     (S[A"-dllib"; A("dll"^lib)]);
412
  
413
                   (* When ocaml link something that use the C library, then one
414
                      need that file to be up to date.
415
                    *)
416
                   dep  ["link"; "ocaml"; "use_lib"^lib] 
417
                     [dir/"lib"^lib^"."^(!Options.ext_lib)];
418
  
419
                   (* TODO: be more specific about what depends on headers *)
420
                   (* Depends on .h files *)
421
                   dep ["compile"; "c"] 
422
                     headers;
423
  
424
                   (* Setup search path for lib *)
425
                   flag ["link"; "ocaml"; "use_"^lib] 
426
                     (S[A"-I"; P(dir)]);
427
              )
428
              t.lib_c;
429
  
430
              (* Add flags *)
431
              List.iter
432
              (fun (tags, cond_specs) ->
433
                 let spec = 
434
                   BaseEnvLight.var_choose cond_specs env
435
                 in
436
                   flag tags & spec)
437
              t.flags
438
        | _ -> 
439
            ()
440
  
441
  let dispatch_default t =
442
    dispatch_combine 
443
      [
444
        dispatch t;
445
        MyOCamlbuildFindlib.dispatch;
446
      ]
447
  
448
end
449
450
451
open Ocamlbuild_plugin;;
452
let package_default =
453
  {MyOCamlbuildBase.lib_ocaml = []; lib_c = []; flags = []; }
454
  ;;
455
456
let dispatch_default = MyOCamlbuildBase.dispatch_default package_default;;
457
458
(* OASIS_STOP *)
459
Ocamlbuild_plugin.dispatch dispatch_default;;