mad_compile.erl 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. -module(mad_compile).
  2. -copyright('Sina Samavati').
  3. -compile(export_all).
  4. compile(Params) ->
  5. { Cwd, ConfigFile, Conf } = mad_utils:configs(),
  6. Res = case Params of
  7. [] -> mad_compile:'compile-deps'(Cwd, ConfigFile, Conf);
  8. __ -> mad_compile:deps(Cwd, Conf, ConfigFile, [Params])
  9. end,
  10. case bool(Res) of
  11. true -> {error,Params};
  12. false -> mad_compile:'compile-apps'(Cwd, ConfigFile, Conf) end.
  13. deps(_, _, _, []) -> {ok,deps};
  14. deps(Cwd, Conf, ConfigFile, [H|T]) ->
  15. {Name, _} = mad_deps:name_and_repo(H),
  16. Res = case get(Name) == compiled of
  17. true -> {ok,[]};
  18. _ -> dep(Cwd, Conf, ConfigFile, Name) end,
  19. case bool(Res) of
  20. true -> {error,Name};
  21. false -> deps(Cwd, Conf, ConfigFile, T) end.
  22. bool({ok,_}) -> false;
  23. bool({error,_}) -> true.
  24. dep(Cwd, _Conf, ConfigFile, Name) ->
  25. DepsDir = filename:join([mad_utils:get_value(deps_dir, _Conf, ["deps"])]),
  26. DepPath = filename:join([Cwd, DepsDir, Name]),
  27. mad:info("==> ~p~n",[Name]),
  28. DepConfigFile = filename:join(DepPath, ConfigFile),
  29. Conf = mad_utils:consult(DepConfigFile),
  30. Conf1 = mad_script:script(DepConfigFile, Conf, Name),
  31. Deps = mad_utils:get_value(deps, Conf1, []),
  32. DepsRes = bool(deps(Cwd, Conf, ConfigFile, Deps)),
  33. SrcDir = filename:join([mad_utils:src(DepPath)]),
  34. AllFiles = files(SrcDir,".yrl") ++
  35. files(SrcDir,".xrl") ++
  36. files(SrcDir,".erl") ++ % comment this to build with erlc/1
  37. files(SrcDir,".app.src"),
  38. Files = case mad_utils:get_value(erl_first_files, Conf1, []) of
  39. [] -> AllFiles;
  40. FirstFiles ->
  41. FirstFiles1 = lists:map(fun (F) -> filename:join(SrcDir, F ++ ".erl") end, FirstFiles),
  42. FirstFiles1 ++ lists:filter(fun (F) -> lists:member(F, FirstFiles) == false end, AllFiles)
  43. end,
  44. case Files of
  45. [] -> {ok,Name};
  46. Files ->
  47. IncDir = mad_utils:include(DepPath),
  48. EbinDir = mad_utils:ebin(DepPath),
  49. LibDirs = mad_utils:get_value(lib_dirs, Conf, []),
  50. Includes = lists:flatten([
  51. [{i,filename:join([DepPath,L,D,include])} || D<-mad_utils:raw_deps(Deps) ] % for -include
  52. ++ [{i,filename:join([DepPath,L])}] || L <- LibDirs ]), % for -include_lib
  53. %mad:info("DepPath ~p~n Includes: ~p~nLibDirs: ~p~n",[DepPath,Includes,LibDirs]),
  54. % create EbinDir and add it to code path
  55. file:make_dir(EbinDir),
  56. code:replace_path(Name,EbinDir),
  57. Opts = mad_utils:get_value(erl_opts, Conf1, []),
  58. FilesStatus = compile_files(Files,IncDir, EbinDir, Opts,Includes),
  59. DTLStatus = mad_dtl:compile(DepPath,Conf1),
  60. PortStatus = lists:any(fun(X)->X end,mad_port:compile(DepPath,Conf1)),
  61. put(Name, compiled),
  62. case DepsRes orelse FilesStatus orelse DTLStatus orelse PortStatus of
  63. true -> {error,Name};
  64. false -> {ok,Name} end end.
  65. compile_files([],_,_,_,_) -> false;
  66. compile_files([File|Files],Inc,Bin,Opt,Deps) ->
  67. case (module(filetype(File))):compile(File,Inc,Bin,Opt,Deps) of
  68. true -> true;
  69. false -> compile_files(Files,Inc,Bin,Opt,Deps);
  70. X -> mad:info("Compilation Error: ~p~n",[{X,File}]), true end.
  71. module("erl") -> mad_erl;
  72. module("erl.src") -> mad_utils;
  73. module("yrl") -> mad_yecc;
  74. module("xrl") -> mad_leex;
  75. module("app.src") -> mad_app;
  76. module(_) -> mad_none.
  77. filetype(Path) -> string:join(tl(string:tokens(filename:basename(Path), ".")), ".").
  78. files(Dir,Ext) -> filelib:fold_files(Dir, Ext, true, fun(F, Acc) -> [F|Acc] end, []).
  79. is_compiled(BeamFile, File) -> mad_utils:last_modified(BeamFile) >= mad_utils:last_modified(File).
  80. 'compile-apps'(Cwd, ConfigFile, Conf) ->
  81. Dirs = mad_utils:sub_dirs(Cwd, ConfigFile, Conf),
  82. [put(D,0)||D<-Dirs],
  83. case Dirs of
  84. [] -> mad_compile:dep(Cwd, Conf, ConfigFile, Cwd);
  85. Apps -> mad_compile:dep(Cwd, Conf, ConfigFile, Cwd),
  86. mad_compile:deps(Cwd, Conf, ConfigFile, Apps) end.
  87. 'compile-deps'(Cwd, ConfigFile, Conf) ->
  88. mad_compile:deps(Cwd, Conf, ConfigFile, mad_utils:get_value(deps, Conf, [])).
  89. list(X) when is_atom(X) -> atom_to_list(X);
  90. list(X) -> X.