Netsupport for Linux. (simple client server)

Linux specific questions.
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Netsupport for Linux. (simple client server)

Post by D.J.Peters »

Out of date use: Simple Network Connection instead.

Joshy
Last edited by D.J.Peters on Nov 03, 2021 0:33, edited 9 times in total.
marzec
Posts: 225
Joined: Jun 06, 2005 23:17

Post by marzec »

kwelness.

why did you write the main functionality in asm? i guess just for training purposes right? oh and it's receive not resive, but that's just a minor thing. also functionality to have non blocking sockets would be nice i guess. i'm not quiet sure what int 80 provides you with but if it's the berkley socket stuff then you'll probably have problems with your send routine as it might not send all the data. with berkley sockets you have to check the return value of send() that will return how many bytes have actually been send. i guess you'll have to do that too in your netSend function.
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

marzec wrote:why did you write the main functionality in asm?
You can't call the Linux kernel in FreeBASIC.
marzec wrote:i guess just for training purposes right?
No i write in assembler since last 25 years.
marzec wrote:with berkley sockets you have to check the return value of send() that will return how many bytes have actually been send

Code: Select all

SendAnyData:
len=NetWrite(socket,lpBuffer,BufferSize)
if len<0 then
  'error: or try it again
elseif len<BufferSize then
  BufferSize-=len:lpBufer+=BufferSize:goto SendAnyData
end if
Joshy
Last edited by D.J.Peters on Apr 23, 2007 21:29, edited 1 time in total.
E.K.Virtanen
Posts: 785
Joined: May 28, 2005 9:19
Location: Finland

Post by E.K.Virtanen »

*hails to D.J.Peters*
=)
marzec
Posts: 225
Joined: Jun 06, 2005 23:17

Post by marzec »

whoopsi :p it was 4am when i read it forgive me hehe. well done ( though i wonder why you are going the kernel way, writting it with berkley sockets would have been more portable ) nice thingo
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

marzec wrote:...writting it with berkley sockets would have been more portable
Portable to what ?

Joshy
Last edited by D.J.Peters on Apr 23, 2007 21:29, edited 1 time in total.
marzec
Posts: 225
Joined: Jun 06, 2005 23:17

Post by marzec »

windows most probably :p
Shadowwolf
Posts: 341
Joined: May 27, 2005 7:01
Location: Canada
Contact:

Post by Shadowwolf »

or any other platform that conforms to berkley sockets.
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

Code: Select all

enum ADDR_FAMILIES
  AF_UNSPEC  = 0 ' Unspecified.
  AF_LOCAL       ' Local to host (pipes and file-domain).
  AF_INET        ' IP protocol family.
  AF_AX25        ' Amateur Radio AX.25.
  AF_IPX         ' Novell Internet Protocol.
  AF_APPLETALK   ' Appletalk DDP.
  AF_NETROM      ' Amateur radio NetROM.
  AF_BRIDGE      ' Multiprotocol bridge.
  AF_ATMPVC      ' ATM PVCs.
  AF_X25         ' Reserved for X.25 project.
  AF_INET6       ' IP version 6.
  AF_ROSE        ' Amateur Radio X.25 PLP.
  AF_DECnet      ' Reserved for DECnet project.
  AF_NETBEUI     ' Reserved for 802.2LLC project.
  AF_SECURITY    ' Security callback pseudo AF.
  AF_KEY         ' PF_KEY key management API.
  AF_NETLINK     ' PF_ROUTE=16 Alias to emulate 4.4BSD.
  AF_PACKET      ' Packet family.
  AF_ASH         ' Ash.
  AF_ECONET      ' Acorn Econet.
  AF_ATMSVC      ' ATM SVCs.
  AF_21
  AF_SNA         ' Linux SNA Project
  AF_IRDA        ' IRDA sockets.
  AF_PPPOX       ' PPPoX sockets.
  AF_WANPIPE     ' Wanpipe API sockets.
end enum
Sorry but i have never used sockets before and can't understood your berklay questions.
All aps in Linux used the sockets per CLib or syscall 2. I have only read the man pages.

What is missing in the address / protol family list?

If you mean the diffrent coding of the addressspace 192.168.0.1 than you can write your neaded macro self.

For blocking sockets you nead "select".

Joshy
Last edited by D.J.Peters on Apr 23, 2007 21:30, edited 1 time in total.
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

link removed it was to sexy :-)
Last edited by D.J.Peters on Apr 23, 2007 21:31, edited 4 times in total.
marcov
Posts: 3504
Joined: Jun 16, 2005 9:45
Location: Netherlands
Contact:

Post by marcov »

D.J.Peters wrote: Sorry but i have never used sockets before and can't understood your berklay questions.
Nearly all sockets are Berkeley (BSD) sockets. See e.g. the manual pages of this. You linux code is Berkeley sockets code. (and way more comformant than that Windows abhorration called Winsock
All aps in Linux used the sockets per CLib or syscall 2. I have only read the man pages.
Which will hopefully note that these are Berkeley socket functions. If not literally then in some history paragraph showing that they derive from BSD. (sockets are a BSD/Berkeley invention, the B in BSD= Berkeley Software Distribution)
For blocking sockets you nead "select".
Select is a pain. Watch out with it IIRC fdset differs in number of selectors between userland (libc) and kernel.

Of course you'll have to rewrite all this assembler again for FreeBSD, amd64 etc etc, since the exact syscall rules differ slightly from OS to OS and even with version.

Best is to make a syscall abstraction that takes n 32-bit parameters (I called the functions syscall0..syscall7) and code everything with that. Using that abstraction, the calls are nearly the same and much more maintainable. (64-bit parameters on 64-bit OSes btw)

This is still not perfect (e.g. 64-bit arguments on 32-bit systems is troublesome), but already saves a lot of work. It won't save you for sockets though, most other unices multiplex socket functions not over one syscall (socketcall), but have a call for each function.

Example (tsysparam=tsysresult=32bits unsigned, note this code is pic enabled)

http://www.freepascal.org/cgi-bin/viewc ... iew=markup

the syscall functions coded with them on Linux:

http://www.freepascal.org/cgi-bin/viewc ... iew=markup

now the same on freebsd:

http://www.freepascal.org/cgi-bin/viewc ... iew=markup

Notice how similar they are?
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

Hello marcov thank you for your feedback in this time FreeBASIC is for x86 Linux only and i have tested last week all what you can do with sockets in blocking or non blocking mode with select and fctl and all was working fine. If you debug C apps or use strace you can see all use the kernel gate for Linux x86 sockets.

And now for FreeBASIC users the code is the same for Win and Lin with the wrapper for names

Net(Socket,Bind,Listen,Accept,Accept,WriteRead,Send/ReciveString,GetPeer/Hostname)

If you write portable code then i sugest you write it in C not FreeBASIC all Linux / *NIX headers are in C not in FreeBASIC.

If i have time (curently i write FBSound for Lin and Win) i will read your posted links.

Again thanx for your message.

Joshy
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

If you need simple HTTP GET request to download a webseit or file you need only 5 calls.
1. NetSocket create socket
2. NetGetHostByName get ip from server domain
3. NetConnect connect to server
4. NetSendString send an HTTP GET request
5. NetRecivString get the site or file (as simple string)

same code as the Windows version
http://www.freebasic.net/forum/viewtopi ... 6972#26972

Code: Select all

' wingetfile.bas

#include "net.bi"

Dim As WSADATA     wsData
Dim As FDSOCKET    hClient,hServer
Dim As SOCKADDR_in ServerAddr,Iam
Dim As HOSTENT Ptr lpResolver
Dim As String      msg,host
Dim As Integer     ret

ret=WSAStartup(VERSION_11,@wsData)
If ret<>0 Then ? "error: wsastartup!":End 1

hClient=NetSocket(AF_INET,SOCK_STREAM)
If hClient<0 Then
  ? "error: create socket!"
  WSACleanup
  Sleep:End 2
End If

'get ip from domain
lpResolver=NetGetHostByName ("www.alice-dsl.net")
If lpResolver=0 Then
  ? "error: NetGetHostByName!"
  WSACleanup
  Sleep:End 3
End If

With ServerAddr
  .sin_family = AF_INET
  .sin_port   = htons(80)  ' Port 80 in network byte order
  .sin_addr   = *lpResolver->h_addr_ip_list[0] ' ip from server
End With

ret=NetConnect(hClient,@ServerAddr)
If ret<0 Then
  ? "error: can't connect to server!"
  WSACleanup
  Sleep:End 4
End If

Print "get file test.txt"
host="alice-dsl.net"
'the GET request
msg="GET /d.j.peters/test.txt HTTP/1.1"               + Chr(13) + Chr(10) 'line terminator
msg=msg + "User-Agent: Wer_will_das_wissen?" + Chr(13) + Chr(10) 'line terminator
msg=msg + "Host: " + host                    + Chr(13) + Chr(10) 'line terminator
msg=msg + "Accept: text/html;text/plain"     + Chr(13) + Chr(10) 'line terminator
msg=msg + Chr(13) + Chr(10) 'header terminator

ret=NetSendString(hClient,msg)
If ret<=0 Then
  ? "error: send string!"
  NetClose hClient
  WSACleanup
  Sleep:End 6
End If

ret=NetReciveString(hClient,msg)
NetClose hClient
WSACleanup

If ret<0 Then
  ? "error: get file/site!"
Else
  ? "Answer from server"
  ? "----------------------------"
  ? msg
  'optional save it
  'open exepath + "\answer.txt" for output as #1
  'print #1,msg
  'close #1
End If 
Sleep
End
If you have a running connecsion try it out.

Joshy
Last edited by D.J.Peters on Apr 23, 2007 21:23, edited 2 times in total.
D.J.Peters
Posts: 8642
Joined: May 28, 2005 3:28
Contact:

Post by D.J.Peters »

Send eMail via an smtp server ported by Porfirio.

Joshy

Code: Select all

'Based on PureBasic code from:
' German forum: http://robsite.de/php/pureboard/viewtopic.php?t=765
' Author: stbi
' Date: 30. April 2003
'FreeBasic code by
' Author: Porfirio
' Date:30 03 2006

#include "net.bi"
option explicit

'Define vars
dim as FDSOCKET hClient
dim as SOCKADDR_in ServerAddr
dim As HOSTENT ptr lpResolver
dim as string res, cr, FBMailerLog
dim as string server,mailfrom,mailto,subject,msgbody
cr=Chr(13)+Chr(10)

server="requied"         'ex. smtp.gmail.com
mailfrom="requied"   'ex. example.gmail.com
mailto="requied" 'ex. friend.gmail.com
subject="the header"                 'ex. Hi Friend
msgbody="The message to be send"     'ex. Firstline message+cr+Second line message :)

'create socket
hClient=NetSocket(AF_INET,SOCK_STREAM)
if hClient<0 then
  FBMailerLog+="error: create socket!"
end if

'get the host
lpResolver=NetGetHostByName (server)
if lpResolver=0 then
  FBMailerLog+="error: NetGetHostByName!"
end if

with ServerAddr
  .sin_family = AF_INET
  .sin_port   = htons(25)  ' SMTP port
  .sin_addr   = *lpResolver->h_addr_ip_list[0] ' ip from server
end with

if NetConnect(hClient,@ServerAddr)<0 then
  FBMailerLog+="error: can't connect to server!"
end if

NetReciveString(hClient,res)
FBMailerLog+=res
if Left(res,3)="220" then
    NetSendString(hClient,"HELO CGIapp"+cr)
    NetReciveString(hClient,res)
    FBMailerLog+=res
    if Left(res,3)="250" then
        sleep(100)
        NetSendString(hClient,"MAIL FROM: <"+mailfrom+">"+cr)
        NetReciveString(hClient,res)
        FBMailerLog+=res
        if Left(res,3)="250" then
            NetSendString(hClient,"RCPT TO: <"+mailto+">"+cr)
            NetReciveString(hClient,res)
            FBMailerLog+=res
            if Left(res,3)="250" then
                NetSendString(hClient,"DATA"+cr)
                NetReciveString(hClient,res)
                FBMailerLog+=res
                if Left(res,3)="354" then
                    sleep(100)
                    NetSendString(hClient,"Date: Wed, 28 Mar 2006 13:21:20 GMT"+cr)
                    NetSendString(hClient,"From: Mach4D network<"+mailfrom+">"+cr)
                    NetSendString(hClient,"To: Porf-Master<"+mailto+">"+cr)
                    NetSendString(hClient,"Subject: "+subject+cr)
                    NetSendString(hClient,"X-Mailer: FBMailer"+cr)
                    NetSendString(hClient,"Message-Id: <123 @FBmailer>")
                    sleep(100)
                    NetSendString(hClient,"--"+cr+"--"+cr+cr)
                    NetSendString(hClient,msgbody)
                    sleep(100)
                    NetSendString(hClient,""+cr)
                    NetSendString(hClient,"."+cr)
                    NetReciveString(hClient,res)
                    FBMailerLog+=res
                    if Left(res,3)="250" then
                      sleep(100)
                      NetSendString(hClient,"QUIT"+cr)
                      dim as string a
                      NetReciveString(hClient,res)
                      FBMailerLog+=res
                      ? "mail sended"
                      ? FBMailerLog
                    end if
                end if
            end if
        end if
    end if
end if

NetClose hClient

? "press q to quit"
DO
LOOP UNTIL INKEY$ = "q"
TbbW
Posts: 348
Joined: Aug 19, 2005 10:08
Contact:

Post by TbbW »

KICK ASS! :D
finaly linux suport for sockets without sdl_net :)
Post Reply