CallDLL ws2_32.dll - help needed

Blitz3D Forums/Blitz3D Beginners Area/CallDLL ws2_32.dll - help needed

Sarakan(Posted 2004) [#1]
1. How would I write a decls for the gethostname function?
2. Failing #1...I wish to make Blitz functions for all functions within "ws2_32.dll"

hostname$ = GetHostName()
Print hostname$
WaitKey()
End


Function GetHostName$()
	tempbuffer$ = String$(" ", 63)
	tempbank = CreateBank(Len(tempbuffer$)+4)
	PokeByte tempbank,Len(tempbuffer$),4
	CallDLL ("ws2_32.dll", "gethostname", tempbank)
	For temp = 0 To Len(tempbuffer$)-1
		tempbyte = PeekByte (tempbank,temp)
		If tempbyte <> 0 Then tempname$ = tempname$ + Chr$(PeekByte (tempbank,temp))
	Next
	FreeBank tempbank
	Return tempname$
End Function



Sarakan(Posted 2004) [#2]
FYI:
Print GetEnv$("COMPUTERNAME") ;will return the hostname in all caps
GetHostName$()                ;returns as the system sees it



Sarakan(Posted 2004) [#3]
Does anyone understand the hostent structure?
struct hostent
{
  char *h_name;			/* Official name of host.  */
  char **h_aliases;		/* Alias list.  */
  int h_addrtype;		/* Host address type.  */
  int h_length;			/* Length of address.  */
  char **h_addr_list;		/* List of addresses from name server.  */
#define	h_addr	h_addr_list[0]	/* Address, for backward compatibility.  */
};


The only thing I get is that the last 4 bytes are the local machine's ip address in reverse.


soja(Posted 2004) [#4]
Generally, I would recommend avoiding CallDLL, which has been deprecated in favor of userlibs/decls.

Here's my example of how to use GetHostName, which works in either B3D or B+.
; .lib "ws2_32.dll"
; GetHostName%(name*, length%):"gethostname"
; (Make sure these two lines occur in a *.decls file in the userlibs folder)

n = CreateBank(256)
failed% = GetHostName(n, BankSize(n)) 
If Not failed Then
	Print BankToString(n)
Else
	Print "Error code: "+failed
EndIf

Function BankToString$(bank)
	While PeekByte(bank, i) <> 0
		s$ = s$ + Chr$(PeekByte(bank, i))
		i = i + 1
	Wend
	Return s$
End Function



soja(Posted 2004) [#5]
As for the hostent structure, it's kind of a pain.

h_name is the address of the first character of the hostname.

h_aliases is the address of the list off addresses of aliases -- you would need to use copymemory or something to get this, I think -- unless you didn't care about it, then that would make it easier for you.

the next two are just normal ints that you can read straight off.

h_addr_list os similar to h_aliases except it contains IP (probably) addresses.

Do you have a more specific question?


Sarakan(Posted 2004) [#6]
Why does h_aliases give a pointer to memory where nothing's at?
And if it helps here is the byte order of the structure as seen by my computer:
Byte(0) = 0
Byte(1) = 0
Byte(2) = 0
Byte(3) = 0
Byte(4) = 156 h_aliases
Byte(5) = 236
Byte(6) = 142
Byte(7) = 9
Byte(8) = 0
Byte(9) = 0
Byte(10) = 0
Byte(11) = 0
Byte(12) = 192 My ip address is 192.168.1.100
Byte(13) = 168
Byte(14) = 1
Byte(15) = 100


soja(Posted 2004) [#7]
Do you have some code I could play with? Or which function are you trying to use?


Sarakan(Posted 2004) [#8]
The following is what I have now:

Print GetHostName$() + " is the computer's hostname"

HOSTENT = GetHostByName( GetHostName$() )
Print PeekInt(HOSTENT ,4) + " is the pointer to the aliases right?"

Print ""
Print "The following bytes are from HOSTENT"
For x = 0 To 15
	Print "Byte (" + x + ") = " +PeekByte (HOSTENT ,x)
Next

WaitKey()
End





Function GetHostByName(LocalHostName$)
	;returns the memory address (integer) to where the HOSTENT is
	Return CallDLL("ws2_32.dll", "gethostbyname",LocalHostName$)
End Function





Function GetHostName$()
	tempbuffer$ = String$(" ", 63)
	tempbank = CreateBank(Len(tempbuffer$)+4)
	PokeByte tempbank,Len(tempbuffer$),4
	CallDLL ("ws2_32.dll", "gethostname", tempbank)
	For temp = 0 To Len(tempbuffer$)-1
		tempbyte = PeekByte (tempbank,temp)
		If tempbyte <> 0 Then tempname$ = tempname$ + Chr$(PeekByte (tempbank,temp))
	Next
	FreeBank tempbank
	Return tempname$
End Function



soja(Posted 2004) [#9]
One thing I see right away is that HOSTENT is an actual memory address, and you're using PeekInt as if it reads straight from memory. That won't work. PeekInt reads from a BANK, which is 1 layer of abstraction away from direct memory access. What you should probably do is use RtlMoveMemory (kernel32) to copy the contents at HOSTENT into a bank that you can then read with Peek.

Also, I'm not sure that the third parameter of CallDLL (for gethostbyname) will work with a string. It didn't with me. Instead of using LocalHostName$, I would use what's in tempbank (from the GetHostName function, but global).

Is there some reason why you're using CallDLL instead of decls files?


Sarakan(Posted 2004) [#10]
Yes I don't understand how to create a wrapper (which I've been told I need to do if I want to ensure the user of these functions don't see the banks involved) ...



fyi...I'm learning Winsock so I can learn ICMP.dll :> (I'd like to be able to ping in bb)


Sarakan(Posted 2004) [#11]
And Soja, I'd thought that the Hostent pointer [received from GetHostByName()] was the same kind of pointer that Hostent bytes 4-7 [h_aliases] was.