Kod z kompendium dotyczący INDY i UDP – kompiluje się, ale działa nieprawidłowo

0

Męczę się nad przykładem: INDY

wszystko się ładnie kompiluje i uruchamia ale w memo1 nie pojawiają się wpisane dane w edit1.
Czy ktoś sprawdzał ten kod u siebie ?

0

kodu nie sprawdzałem, może zapora blokuje transmisję danych

EDT
teraz widzę że w przykładzie wszystko chodzi na 'localhoscie' więc to pewnie nie zapora

0

No raczej nie zapora ale coś windows jdnak krzyknął i trzeba było zezwolić na dostęp ale jednak nie działa. Możliwe że jeszcze trzeba ustawić/przestawić jakieś właściwości dla obiektów clienta i serwera?

1

żeby mieć pewność, że to nic związanego z danym kompem/systemem - wklej jako załącznik do posta wersję EXE, odpalimy u nas i zobaczymy, jak się aplikacja zachowuje. Powinno rzucić to jakieś nowe światło na temat ;)

0

OK teraz nie mam komputera z delphi, wieczorem dopiero będę mógł to zrobić ale sprawdzałem na innym kompie i też nie działało.

1

Dobra, zrobiłem u siebie małe testy i ... u mnie działa :D

Pierwsza sprawa - jakiej wersji Delphi oraz Indy używasz? Bo u mnie (Delphi 10.2 Tokyo oraz Lazarus 1.8.4) parametry zdarzenia OnUDPRead są inne, niż w podanym przykładzie. Co zresztą nie jest dziwne, bo podany tutorial jest sprzed 13 lat...

Jak podeślesz wieczorem EXE'ka to będę mógł sprawdzić, czy Twoja wersja u mnie czy działa.

Podczas testów musiałem wyłączyć antyvira i firewalla, bo co chwila narzekały, po pozwoleniu na działanie apka śmigała, aczkolwiek 2 razy miałem totalne zwiechy systemu, które się skończyły hard-resetem. Nie wiem z czego to wynikało, aczkolwiek wczoraj wieczorem Win10 mi się zaktualizował do nowej wersji i może to mieć jakiś związek... Na ogół jest tak, że jak wyłączając system mam komunikat o aktualizacji, to następnego dnia czeka na mnie kilka niespodzianek...

Poniższy kod u mnie działa bezproblemowo. Jak pewnie zauważyłeś - inaczej wygląda obsługa OnUDPRead - została dostosowana do aktualnej wersji Indy. Nie pamiętam szczegółów, ale chyba przesiadka z wersji 9 na 10 INDY to była mała rewolucja, a kod podany w przykładzie jest raczej pisany zgodnie ze starym standardem.

Zauważ też, że procedura do zdarzenia OnStatus nie zostaje wywołana. Szczerze mówiąc nie chce mi się teraz tematu zgłębiać, póki co można to wywalić, aplikacja działa tak, jak sobie życzyłeś :) Kompiluje się zarówno na Delphi, jak i na Lazarusie.

unit Unit1;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
  Vcl.Controls, Vcl.Forms, Vcl.Dialogs, IdUDPServer, IdBaseComponent,
  IdComponent, IdUDPBase, IdUDPClient, Vcl.StdCtrls, IdGlobal, IdSocketHandle;

type
  TForm1 = class(TForm)
    Edit1: TEdit;
    Memo1: TMemo;
    Button1: TButton;
    IdUDPClient1: TIdUDPClient;
    IdUDPServer1: TIdUDPServer;
    procedure FormCreate(Sender: TObject);
    procedure Button1Click(Sender: TObject);
    procedure IdUDPServer1Status(ASender: TObject; const AStatus: TIdStatus;
      const AStatusText: string);
    procedure IdUDPServer1UDPRead(AThread: TIdUDPListenerThread;
      const AData: TIdBytes; ABinding: TIdSocketHandle);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
  IdUDPClient1.Host := '127.0.0.1';
  IdUDPClient1.Send(Edit1.Text);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Edit1.Clear;
  Memo1.Clear;
  IdUDPClient1.Port := 36000;
  IdUDPServer1.DefaultPort := 36000;
  IdUDPServer1.Active := true;
end;

procedure TForm1.IdUDPServer1Status(ASender: TObject; const AStatus: TIdStatus;
  const AStatusText: string);
begin
  Memo1.Lines.Add(AStatusText);
  showmessage('status');
end;

procedure TForm1.IdUDPServer1UDPRead(AThread: TIdUDPListenerThread;
  const AData: TIdBytes; ABinding: TIdSocketHandle);
var
  sText: string;
begin
  Memo1.Lines.Add(ABinding.PeerIP);
  SetString(Stext, PAnsiChar(@AData[0]), Length(AData));
  Form1.Memo1.Lines.Add(sText);
end;

end.
1

Żeby nie robić zamieszania, dodałem "moje" wersje EXE w osobnym poście.
Weź odpal je u siebie i sprawdź, czy działają. Jak pisałem wcześniej - sprawdzone, u mnie obie działają na 100%. Jeśli u Ciebie nie pójdą, to znaczy, że wina leży po stronie systemu, a nie samej aplikacji.

1

No to uruchomiłem ten exe i wszystko działa, moj nie działa niestety czyli coś mam nie tak. Inaczej też na ten program reaguje windows w moim wyskoczyło tylko jedno okno a w tym dwa.

1

Za bardzo nie rozumiem co oznacza, że wyskoczyło jedno albo dwa okna, ale podejrzewam, że chodzi o jakieś komunikaty z firewalla/antywirusa. Być może w jednym przypadku wyskoczył tylko windowsowy wbudowany firewall, a w drugim masz jeszcze jakieś dodatkowe narzędzie pilnujące porządku w systemie.
W każdym razie - skoro działa, to sprawdź jeszcze w domu, a następnie postaraj się skompilować u siebie kod, który wkleiłem chwilę wcześniej. Zobaczymy, co z tego wyniknie :D

0

No muszę jeszcze raz przepatrzeć wszystko może to tylko jakaś drobnostka jest. Tylko nie widzę pliku źródłowego żeby porównać.

4

Może głupie pytanie ale były na tym forum takie przypadki więc zapytam. Kod skopiowałeś z tego przykładu czy wpisałeś do odpowiednich zdarzeń? Bo jeśli jest kod zdarzenia bez podpięcia w komponencie to nie ma prawa zadziałać.

0

Wszystko sprawdzę wieczorem jak będę przed komputerem i się odezwę. na razie dzięki wielkie.

1

@Deniss77: ogólnie chodzi o to, że komponenty leżące na formularzu muszą mieć podpięte zdarzenia, które znajdują się w module okna. Możesz to sprawdzić w oknie inspektora obiektów, ale też bezpośrednio w pliku .dfm, bo tam te informacje się znajdują i z nich korzysta środowisko.

1

@Deniss77: mamy już wieczór. Czy coś się w temacie ruszyło? :)

0

Tak ruszyło się ale dopiero dzisiaj doszedłem co było nie tak wczoraj miałem za dużo pracy żeby się za to zabrać. I problem był po mojej stronie a dokładniej ułatwiałem sobie życie i żeby nie pisać za dużo to robiłem tak że kopiowałem sobie linijki kodu i wklejałem do zdarzeń obiektów servera i clienta ale jedno zdarzenie zostało tylko wklejone a więc nie przypisane do obiektu i tyle nerwa mi popsuło.

0

Ale teraz mam pytanie odnośnie działania UDP. Generalnie jest sobie server i klient są zupełnie od siebie niezależne, serwer tylko nasłuchuje co do niego przychodzi na konkretnym porcie, wie z jakiego IP przyszła do niego wiadomość a adres serwera jest adresem IP karty sieciowej komputera. Client potrafi tylko wysłać wiadomość do servera na konkretnym porcie.
Chcąc zrealizować komunikację dwustronną między urządzeniami poprzez UDP każde z tych urządzeń musi posiadać clienta do wysyłania oraz server do nasłuchu czy dobrze to rozumiem?
I jeszcze jedno zagadnienie bo nie daje mi to spokoju a pojawia się w różnych opisach a mianowicie czym są gniazda czyli sockety, czy to nie chodzi o porty?

1

Tak lekko upraszczając, możemy porównać całość do centrali telefonicznej ;)
Adres IP komputera to jakby numer "zewnętrzny" centrali, czyli ten numer, na który dzwonisz np. do urzędu lub jakiejś firmy.
Z kolei port jest numerem wewnętrznym.
Różne usługi mogą nasłuchiwać na różnych portach. Jeśli próbujesz się połączyć z danym numerem wewnętrznym to po dodzwonieniu się do centrali i jego wybraniu zaczyna dzwonić telefon w jakimś pokoju. Jeśli tam siedzi pani Krysia, to odbierze. Analogicznie w komputerze - jeśli działa i nasłuchuje tam jakaś usługa, to może zostać zestawione połączenie.
A czym jest socket? To jakby "uchwyt", punkt zaczepienia, powstaje z połączenia danego adresu IP i portu, jest łącznikiem aplikacji z podsystemem sieciowym. W sumie to ciężko mi to wyjaśnić, więc może jak rzucisz okiem na dwie definicje to zrozumiesz o co chodzi:
https://pl.wikipedia.org/wiki/Port_protoko%C5%82u
https://pl.wikipedia.org/wiki/Gniazdo_(telekomunikacja)
http://www.steves-internet-guide.com/tcpip-ports-sockets/
Pamiętaj, że żeby było śmieszniej, w wypadku komunikacji sieciowej po obu stronach transmisji możesz mieć różne numery portów.

A tak w ogóle to czemu robisz to w oparciu o UDP a nie TCP?

1

Czemu UDP? - ponieważ od strony mikrokontrolera jest łatwiejsze do zaimplementowania i jakieś doświadczenie z UDP od strony mikrokontrolera było natomiast z TCP trzeba by było zaczynać od zera i na dodatek nie mam kogo nawet spytać jak to opanować od strony mikrokontrolera. Tutaj akurat jest bardzo fajne forum i można uzyskać podpowiedzi jak co zrobić i nikt nikogo nie wyśmiewa, inaczej jest na elektrodzie gdzie ciężko jest o jakąś podpowiedź jak ktoś coś wie to więcej będzie się nabijał niż podpowie a takie tematy jak UDP czy TCP w miktokontrolerze są bardzo sporadyczne.

1

Rozumiem :)
Wcześniej o żadnym kontrolerze nie wspominałeś, więc założyłem sobie, że chodzi o aplikację komunikującą się stricte desktopowo.
Powiedz - co się kryje pod hasłem "kontroler"? Na czym konkretnie to robisz?

0

Czyli socket to zespół niezbędnych parametrów umożliwiających zestawienie komunikacji.

1

Zasadniczo socket jest jakby "zebraniem do kupy" kilku rzeczy związanych z komunikacją. Sam adres IP czy port to za mało żeby nawiązać połączenie, dopiero jak się to wszystko połączy, to powstaje struktura, z którą można się komunikować. Zwróć uwagę, że port czy adres IP są istotne w chwili nawiązywania połączenia, ale po jego zestawieniu możesz o nich zapomnieć, bo dla Ciebie "partnerem" do komunikacji jest socket/gniazdo.

Ponownie, używając porównania do centrali telefonicznej - numery centrali oraz wewnętrzny (czyli w naszym przypadku adres IP oraz port) są potrzebne do dodzwonienia się, ale jak już ktoś po drugiej stronie odbierze, to potem możesz o nich zapomnieć. Dla Ciebie ważny jest aparat telefoniczny, na którym jest połączenie zestawione, to z aparatem prowadzisz rozmowę i cała reszta Cię nie obchodzi. I właśnie socket dla aplikacji jest tym, czym dla człowieka telefon ;)

0

Jest sobie mikroprocesor STM32 który posiada obsługę sprzętową ethernetu tzn ma magistralę RMII umożliwiającą połączenie go ze scalakiem do którego bezpośrednio podłączam gniazdo sieciowe RJ45. Do portów mikroprocesora podłączone są czujniki typu N.O. otwarcia drzwi i wyjścia przekaźnikowe z innych urządzeń. My poprzez sieć komputerową wysyłamy odzwierciedlenie/naruszenie tych urządzeń a oddalona aplikacja w sposób graficzny pokazuje co się dzieje na oddalonym obiekcie.

1

A taki mały offtop - czemu robisz to na mikrokontrolerze, a nie na jakimś "ułatwiaczu" typu Arduino czy RPi?

1

Bo jak kiedyś coś takiego zrobiłem i jak się od pioruna rozsypało po roku i jak chciałem naprawić to się okazało coś bardzo ciekawego:

  • scalaka nie da się kupić bo jest wyprodukowany tylko i wyłącznie pod to urządzenie jakby wyprodukowali ileś tam scalaków tylko do tych urządzeń i tylko dla producenta urządzenia,
  • urządzenia też nie dało się kupić bo było ich tyle ile scalaków i dalszej produkcji nie planowano, oczywiście były jakieś nowsze wersje ale już miały inne wymiary inne gniazda wejściowe generalnie całe otoczenie inne.
    A taki mikrokontroler jest zawsze dostępny mogę też kupić zawsze kilka na zapas, mam też płytkę PCB którą jakby co zawsze mogę przystosować nawet do innego mikrokontrolera.

1 użytkowników online, w tym zalogowanych: 0, gości: 1