Awguri.
Illum nixtieq inħares lejn il-proċess tal-kitba ta 'applikazzjonijiet klijent-server li jwettqu l-funzjonijiet ta' utilitajiet standard tal-Windows, bħal Telnet, TFTP, eċċetera, eċċetera f'Java pur. Huwa ċar li mhux se nġib xejn ġdid - dawn l-utilitajiet kollha ilhom jaħdmu b'suċċess għal aktar minn sena, iżda nemmen li mhux kulħadd jaf x'inhu għaddej taħt il-barnuża.
Dan huwa eżattament dak li se jiġi diskuss taħt il-qatgħa.
F'dan l-artikolu, sabiex ma nkaxkrux, minbarra l-informazzjoni ġenerali, se nikteb biss dwar is-server Telnet, iżda bħalissa hemm ukoll materjal dwar utilitajiet oħra - se jkun f'partijiet ulterjuri tas-serje.
L-ewwelnett, trid tifhem x'inhu Telnet, għalxiex huwa meħtieġ, u għalxiex jintuża. Mhux se nikkwota sorsi verbatim (jekk meħtieġ, se nehmeż link għal materjali dwar is-suġġett fl-aħħar tal-artiklu), se ngħid biss li Telnet jipprovdi aċċess remot għal-linja tal-kmand tal-apparat. B'mod ġenerali, dan huwa fejn tispiċċa l-funzjonalità tagħha (I deliberatament żammejt siekta dwar l-aċċess għall-port tas-server; aktar dwar dan aktar tard). Dan ifisser li biex nimplimentah, għandna bżonn naċċettaw linja fuq il-klijent, ngħadduha lis-server, nippruvaw ngħadduha lil-linja tal-kmand, aqra r-rispons tal-linja tal-kmand, jekk hemm waħda, tgħaddiha lura lill-klijent u juriha fuq l-iskrin, jew, jekk ikun hemm żbalji, ħalli l-utent ikun jaf li xi ħaġa hija ħażina.
Biex nimplimentaw dan ta 'hawn fuq, għalhekk, għandna bżonn 2 klassijiet tax-xogħol u xi klassi tat-test li minnha se nniedu s-server u li permezz tagħhom il-klijent se jaħdem.
Għaldaqstant, bħalissa l-istruttura tal-applikazzjoni tinkludi:
- TelnetClient
- TelnetClientTester
- TelnetServer
- TelnetServerTester
Ejja ngħaddu minn kull wieħed minnhom:
TelnetClient
Din il-klassi kollha għandha tkun kapaċi tagħmel hu li tibgħat kmandi riċevuti u turi r-risposti riċevuti. Barra minn hekk, jeħtieġ li tkun tista 'tqabbad ma' port arbitrarju (kif imsemmi hawn fuq) ta 'apparat remot u skonnettja minnu.
Biex jinkiseb dan, ġew implimentati l-funzjonijiet li ġejjin:
Funzjoni li tieħu indirizz tas-socket bħala argument, tiftaħ konnessjoni u tibda flussi ta 'input u output (il-varjabbli tan-nixxiegħa huma ddikjarati hawn fuq, is-sorsi sħaħ huma fl-aħħar tal-artiklu).
public void run(String ip, int port)
{
try {
Socket socket = new Socket(ip, port);
InputStream sin = socket.getInputStream();
OutputStream sout = socket.getOutputStream();
Scanner keyboard = new Scanner(System.in);
reader = new Thread(()->read(keyboard, sout));
writer = new Thread(()->write(sin));
reader.start();
writer.start();
}
catch (Exception e) {
System.out.println(e.getMessage());
}
}
Tagħbija żejda tal-istess funzjoni, konnessjoni mal-port default - għal telnet dan huwa 23
public void run(String ip)
{
run(ip, 23);
}
Il-funzjoni taqra karattri mit-tastiera u tibgħathom lis-socket tal-output - li huwa tipiku, fil-modalità tal-linja, mhux il-mod tal-karattri:
private void read(Scanner keyboard, OutputStream sout)
{
try {
String input = new String();
while (true) {
input = keyboard.nextLine();
for (char i : (input + " n").toCharArray())
sout.write(i);
}
}
catch (Exception e) {
System.out.println(e.getMessage());
}
}
Il-funzjoni tirċievi data mis-sokit u turiha fuq l-iskrin
private void write(InputStream sin)
{
try {
int tmp;
while (true){
tmp = sin.read();
System.out.print((char)tmp);
}
}
catch (Exception e) {
System.out.println(e.getMessage());
}
}
Il-funzjoni twaqqaf ir-riċeviment u t-trażmissjoni tad-data
public void stop()
{
reader.stop();
writer.stop();
}
}
TelnetServer
Din il-klassi għandu jkollha l-funzjonalità li tirċievi kmand minn socket, tibgħatha għall-eżekuzzjoni, u tibgħat tweġiba mill-kmand lura lis-socket. Il-programm deliberatament ma jiċċekkjax id-dejta tal-input, għaliex l-ewwelnett, anki f'"telnet boxed" huwa possibbli li d-diska tas-server tiġi fformattjata, u t-tieni, il-kwistjoni tas-sigurtà f'dan l-artikolu titħalla barra fil-prinċipju, u huwa għalhekk li m'hemmx kelma dwar encryption jew SSL.
Hemm 2 funzjonijiet biss (waħda minnhom hija mgħobbija żżejjed), u b'mod ġenerali din mhix prattika tajba ħafna, iżda għall-finijiet ta 'dan il-kompitu, deherli xieraq li nħalli kollox kif inhu.
boolean isRunning = true;
public void run(int port) {
(new Thread(()->{ try {
ServerSocket ss = new ServerSocket(port); // создаем сокет сервера и привязываем его к вышеуказанному порту
System.out.println("Port "+port+" is waiting for connections");
Socket socket = ss.accept();
System.out.println("Connected");
System.out.println();
// Берем входной и выходной потоки сокета, теперь можем получать и отсылать данные клиенту.
InputStream sin = socket.getInputStream();
OutputStream sout = socket.getOutputStream();
Map<String, String> env = System.getenv();
String wayToTemp = env.get("TEMP") + "tmp.txt";
for (int i :("Connectednnr".toCharArray()))
sout.write(i);
sout.flush();
String buffer = new String();
while (isRunning) {
int intReader = 0;
while ((char) intReader != 'n') {
intReader = sin.read();
buffer += (char) intReader;
}
final String inputToSubThread = "cmd /c " + buffer.substring(0, buffer.length()-2) + " 2>&1";
new Thread(()-> {
try {
Process p = Runtime.getRuntime().exec(inputToSubThread);
InputStream out = p.getInputStream();
Scanner fromProcess = new Scanner(out);
try {
while (fromProcess.hasNextLine()) {
String temp = fromProcess.nextLine();
System.out.println(temp);
for (char i : temp.toCharArray())
sout.write(i);
sout.write('n');
sout.write('r');
}
}
catch (Exception e) {
String output = "Something gets wrong... Err code: "+ e.getStackTrace();
System.out.println(output);
for (char i : output.toCharArray())
sout.write(i);
sout.write('n');
sout.write('r');
}
p.getErrorStream().close();
p.getOutputStream().close();
p.getInputStream().close();
sout.flush();
}
catch (Exception e) {
System.out.println("Error: " + e.getMessage());
}
}).start();
System.out.println(buffer);
buffer = "";
}
}
catch(Exception x) {
System.out.println(x.getMessage());
}})).start();
}
Il-programm jiftaħ il-port tas-server, jaqra d-dejta minnu sakemm jiltaqa 'ma' karattru tat-tmiem tal-kmand, jgħaddi l-kmand għal proċess ġdid, u jidderieġi mill-ġdid l-output mill-proċess għas-sokit. Kollox huwa sempliċi daqs xkubetta tal-attakk Kalashnikov.
Għaldaqstant, hemm tagħbija żejda għal din il-funzjoni b'port default:
public void run()
{
run(23);
}
Ukoll, għalhekk, il-funzjoni li twaqqaf is-server hija wkoll trivjali, tinterrompi l-linja eterna, u tikser il-kundizzjoni tagħha.
public void stop()
{
System.out.println("Server was stopped");
this.isRunning = false;
}
Mhux se nagħti klassijiet tat-test hawn, huma hawn taħt - kull ma jagħmlu hu li jiċċekkjaw il-funzjonalità tal-metodi pubbliċi. Kollox jinsab fuq il-git.
Fil-qosor, fi ftit filgħaxija tista 'tifhem il-prinċipji ta' tħaddim tal-utilitajiet prinċipali tal-console. Issa, meta aħna telenet għal kompjuter remot, nifhmu x'qed jiġri - il-maġija sparixxa)
Allura, il-links:
Sors: www.habr.com