SDL_Net-kokeiluni jatkuvat (lue https://www.ohjelmointiputka.net/keskustelu/
#include <stdio.h> #include <SDL/SDL.h> #include <SDL/SDL_net.h> void lahetakomento(TCPsocket tcpsock, char komento[]); int main(int a, char *b[]) { IPaddress ip; TCPsocket tcpsock; SDL_Init(0); SDLNet_Init(); SDLNet_ResolveHost(&ip, "osoite", 21); tcpsock = SDLNet_TCP_Open(&ip); lahetakomento(tcpsock, "USER nimi"); lahetakomento(tcpsock, "PASS sala"); lahetakomento(tcpsock, "TYPE I"); lahetakomento(tcpsock, "PASV"); lahetakomento(tcpsock, "STOR tiedosto"); lahetakomento(tcpsock, "QUIT"); SDLNet_TCP_Close(tcpsock); SDLNet_Quit(); SDL_Quit(); return(0); } void lahetakomento(TCPsocket, char komento[]) { int pituus, tulos; pituus = strlen(komento) + 1; //NULL-merkille tilaa tulos = SDLNet_TCP_Send(tcpsock, komento, pituus); }
...mutta tiedosto ei vain lähde palvelimelle. Olen varmasti ymmärtänyt jotain väärin FTP:n toiminnasta. Mitä? :-)
No tuosta nyt ensinnäkin puuttuu sen itse tiedoston lähetys sinne palvelimelle.
Eihän SDL_net osaa itsestään tuon "STOR tiedosto":n perusteella avata "tiedosto":a ja lukea sieltä tavarat ja heittää FTP-palvelimelle :P
Eli täältä löytyi kivasti tietoa FTP:n toiminnasta. Sepostan nyt kuitenkin tähän miten se tiedoston lähettäminen onnistuu.
Kannattaisi ottaa noiden FTP-komentojen vastaus talteen, jos vaikka salasana on väärä, niin ... (ja tässä tarvitset tuon PASV:n vastausta):
Tuohon PASV-komentoon saat vastaukseksi tämän tyylistä:
227 Entering Passive Mode (194,100,161,5,150,224)
Tuosta pitäisi sitten erotella siten, että tuolla sulkujen sisällä pilkuilla erotettuina neljä ensimmäistä on IP-osoite ja sitten kaksi viimeistä portti (Tässä tapauksessa 150*256+224 = 38624, joka siis on portti johon sitten yhdistetään toisella socketilla. Jos jäi vielä epäselväksi mistä tuo *256 tulee niin se tulee siitä, että jokainen pilkulla erotettu on yksi tavu (0-255) ja portti kun voi olla väliltä 0-65535, tarvitaan siihen siten kaksi tavua).
Eli nyt sitten yhdistämme uudella socketilla tuohon osoitteeseen ja porttiin (Tässä tapauksessa 194.100.161.5:38624). Sen jälkeen lähetetään sillä "alkuperäisellä" socketilla tuo STOR-komento, jonka parametriksi annetaan haluttu tiedostonimi. Sitten jos FTP-serveri vastaa siihen että "kaikki kunnossa", voidaan alkaa tunkea toiselle socketille ("siirtosocket") tavaraa jota halutaan tallennettavaksi tiedostoon. Kun ollaan valmiita, suljetaan "siirtosocketti" (varmaan muukin tapa, mutta tämä näytti toimivan kun telnetillä testasin), jolloin "alkuperäiselle" socketille pitäisi tulostua "226 Transfer complete." (koodi 226). Sitten tiedosto on FTP-palvelimella.
Siinä se näin "lyhyesti" sanottuna.
EDIT: Metabolix sanoikin jo tämän edellisessä topicissa, mikset vain tehnyt niin ^^
Kyllä, lukisit itse sen aiemman aiheen kunnolla. Lisäksi kuvittelisin, että FTP arvostaisi rivin lopussa mieluummin rivinvaihtoa kuin nollamerkkiä, kannattaa siis korjata ohjelma näin.
Luin uudelleen aiemman aiheen, ja kun Metabolix selitti: "Tästä siis selviää, että lähetysyhteys pitää muodostaa osoitteeseen 193.229.9.132 porttiin 256*175 + 206 = 45006. Sinne voit sitten lähettää tiedostosi", niin tarkoittaako tuo, että STOR ei itsessään lähetä tiedostoa vaan tavallaan vain avaa yhteyden sen lähettämiseen...? Sitten tuostako pitäisi lähettää tiedostoa palvelinta kohti?
Joo, sinun pitää avataa uusi yhteys, jonne lähetät itse sen tiedon (kertaan tässä nyt jo kahta viestiä, omaani ja Metabolix:n), kun se ohjelmasi ei "vieläkään" osaa itsestään lähettää sitä tiedoston sisältöä.
Kyllä, tuohon osoitteeseen ja porttiin (taas kahdesta viestistä näet mistä saat ne ongittua) pitää yhdistää ja sinne sitten lähettää itse tiedosto.
Olisin kyllä voinnut tietysti aiemmankin topikin lukea, ettei olisi kahteen kertaan selitystä tullut, mutta enpä usko siitä ainakaan haittaa olevan.
Ja tiedoston lähettäminen onnistuu vain STOR tiedosto.pääte -komennolla? Ei mitään hienoja kikkailuja tms.
Ei onnistu! Lues toi Legun ensimmäinen viesti uudestaan ajatuksella.
Tässä on tuollainen purkkaviritys jonka tuossa äsken tein. Kun sitten muutat tuon SDL_net muotoon niin voit samalla sitten parannella ja saat idean tuosta toiminnasta. Ei mikään paras toteutus, jätin jotain tekemistä sinullekin ;)
Saattaa segfaultata (lue: segfaulttaa), jos palvelimelta tulee roskaa, ja muita bugejakin varmasti löytyy (kuten jo sanoin, ei mikään valmis FTP-ohjelma).
Ja sitten jos vaikka salasana on väärä, niin tämä vaan timeouttaa sitten kolmen sekunnin päästä, eikä "tajua" että salasana meni väärin.
BTW, Uplodadasin tuon FTP.c:n palvelimelle tuolla ohjelmalla, joten kyllä se ainakin jotenkuten toimii ^^
EDIT: Sisennykset näköjään hajonneet (hieman)
Mutta häh, "lähettää tiedosto porttiin x osoitteeseen y", mutta miten tämä lähetys sitten tapahtuu? :D
Ei minulla ole mitään käsitystä tiedostojen lähettämisestä. Kyllä minä siis tiedän, että mitä pitäisi tehdä, mutten vain tiedä tapaa!
No katso tuon FTP.c:n send_file()-funktio vaikka aluksi.
Eli tiedosto lähetetään palvelimelle pienissä palasissa ja sitten palvelin kokoaa tiedoston? Minä en linuxia käytä eli varmaan korvaan send-komennon sdl_netin omalla lähetyskomennolla, juu.
Aihe on jo aika vanha, joten et voi enää vastata siihen.