1%% 2%% %CopyrightBegin% 3%% 4%% Copyright Ericsson AB 2004-2016. All Rights Reserved. 5%% 6%% Licensed under the Apache License, Version 2.0 (the "License"); 7%% you may not use this file except in compliance with the License. 8%% You may obtain a copy of the License at 9%% 10%% http://www.apache.org/licenses/LICENSE-2.0 11%% 12%% Unless required by applicable law or agreed to in writing, software 13%% distributed under the License is distributed on an "AS IS" BASIS, 14%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15%% See the License for the specific language governing permissions and 16%% limitations under the License. 17%% 18%% %CopyrightEnd% 19%% 20 21%%---------------------------------------------------------------------- 22%% JInterface Test Utils 23%%---------------------------------------------------------------------- 24-module(jitu). 25 26 27-export([java/3, 28 java/4, 29 java/5, 30 init_all/1, 31 finish_all/1, 32 kill_all_jnodes/0]). 33 34-include("ct.hrl"). 35 36%% 37%% Lots of stuff here are originating from java_client_erl_server_SUITE.erl 38%% (ic) ... 39%% 40 41 42 43java(Java, Dir, ClassAndArgs) -> 44 cmd(Java++" -classpath "++classpath(Dir)++" "++ClassAndArgs). 45 46java(Java, Dir, Class, Args) -> 47 java(Java, Dir, Class++" "++to_string(Args)). 48 49java(Java, Dir, Class, Args, Props) -> 50 java(Java, Dir, Props++" "++Class, Args). 51 52 53 54 55init_all(Config) when is_list(Config) -> 56 case find_executable(["java"]) of 57 false -> {skip,"Found no Java VM"}; 58 Path -> 59 Pid = spawn(fun() -> 60 ets:new(jitu_tab,[set,named_table,public]), 61 receive stop -> ets:delete(jitu_tab) end 62 end), 63 [{java,Path},{tab_proc,Pid}|Config] 64 end. 65 66finish_all(Config) -> 67 kill_all_jnodes(), 68 ?config(tab_proc,Config) ! stop, 69 Config. 70 71kill_all_jnodes() -> 72 Jnodes = ets:tab2list(jitu_tab), 73 [begin 74% ct:pal("Killing OsPid=~w started with ~p",[OsPid,_Cmd]), 75 kill_os_process(os:type(),integer_to_list(OsPid)) 76 end || {OsPid,_Cmd} <- Jnodes], 77 ets:delete_all_objects(jitu_tab), 78 ok. 79 80kill_os_process({win32,_},OsPid) -> 81 os:cmd("taskkill /PID " ++ OsPid); 82kill_os_process(_,OsPid) -> 83 os:cmd("kill " ++ OsPid). 84 85 86%% 87%% Internal stuff... 88%% 89 90 91find_executable([]) -> 92 false; 93find_executable([E|T]) -> 94 case os:find_executable(E) of 95 false -> find_executable(T); 96 Path -> Path 97 end. 98 99to_string([H|T]) when is_integer(H) -> 100 integer_to_list(H)++" "++to_string(T); 101to_string([H|T]) when is_atom(H) -> 102 atom_to_list(H)++" "++to_string(T); 103to_string([H|T]) when is_pid(H) -> 104 pid_to_list(H)++" "++to_string(T); 105to_string([H|T]) when is_list(H) -> 106 lists:flatten(H)++" "++to_string(T); 107to_string([]) -> []. 108 109% javac(Dir, File) -> 110% cmd("javac -d "++Dir++" -classpath "++classpath(Dir)++" "++ 111% filename:join(Dir, File)). 112 113classpath(Dir) -> 114 {PS,Quote,EscSpace} = 115 case os:type() of 116 {win32, _} -> {";","\"",""}; 117 _ -> {":","","\\"} 118 end, 119 es(Dir++PS++ 120 filename:join([code:lib_dir(jinterface),"priv","OtpErlang.jar"])++PS++ 121 os:getenv("CLASSPATH", ""), 122 Quote, 123 EscSpace). 124 125es(L,Quote,EscSpace) -> 126 Quote++lists:flatmap(fun($ ) -> 127 EscSpace++" "; 128 (C) -> 129 [C] 130 end,lists:flatten(L)) ++ Quote. 131 132cmd(Cmd) -> 133 PortOpts = [{line,80},eof,exit_status,stderr_to_stdout], 134 io:format("cmd: ~ts~n", [Cmd]), 135 case catch open_port({spawn,Cmd}, PortOpts) of 136 Port when is_port(Port) -> 137 case erlang:port_info(Port,os_pid) of 138 {os_pid,OsPid} -> 139 ets:insert(jitu_tab,{OsPid,Cmd}); 140 _ -> 141 ok 142 end, 143 Result = cmd_loop(Port, []), 144 io:format("cmd res: ~w~n", [Result]), 145 case Result of 146 0 -> ok; 147 ExitCode when is_integer(ExitCode) -> {error,ExitCode}; 148 Error -> Error 149 end; 150 {'EXIT',Reason} -> 151 {error,Reason} 152 end. 153 154cmd_loop(Port, Line) -> 155 receive 156 {Port,eof} -> 157 receive 158 {Port,{exit_status,ExitStatus}} -> 159 ExitStatus 160 after 1 -> 161 undefined 162 end; 163 {Port,{exit_status,ExitStatus}} -> 164 receive 165 {Port,eof} -> 166 ok after 1 -> ok end, 167 ExitStatus; 168 {Port,{data,{Tag,Data}}} -> 169 case Tag of 170 eol -> 171 io:put_chars([Line|cr_to_nl(Data)]), 172 io:nl(), 173 cmd_loop(Port, []); 174 noeol -> 175 cmd_loop(Port, [Line|cr_to_nl(Data)]) 176 end; 177 {'EXIT',Port,Reason} -> 178 {error,Reason}; 179 Other -> 180 io:format("WARNING: Unexpected at ~s:~p: ~p~n", 181 [?MODULE_STRING,?LINE,Other]), 182 cmd_loop(Port, Line) 183 end. 184 185%% Convert lonely CR to NL, and CRLF to NL 186%% 187cr_to_nl([$\r,$\n|T]) -> 188 [$\n|cr_to_nl(T)]; 189cr_to_nl([$\r|T]) -> 190 [$\n|cr_to_nl(T)]; 191cr_to_nl([C|T]) -> 192 [C|cr_to_nl(T)]; 193cr_to_nl([]) -> 194 []. 195