--- a/Socket.st Fri Jan 18 15:15:59 2002 +0100
+++ b/Socket.st Mon Jan 28 15:29:28 2002 +0100
@@ -684,339 +684,382 @@
examples
"
example (get help info from an nntp server):
- [exBegin]
- |sock host|
-
- host := OperatingSystem getEnvironment:'NNTPSERVER'.
-
- sock := Socket newTCPclientToHost:host port:'nntp'.
- Transcript showCR:sock nextLine.
- sock buffered:false.
-
- sock nextPutAll:'HELP'; cr.
- [:exit |
- |line|
-
- line := sock nextLine.
- line = '.' ifTrue:[exit value:nil].
- Transcript showCR:line.
- ] loopWithExit.
- sock close
- [exEnd]
+ [exBegin]
+ |sock host|
+
+ host := OperatingSystem getEnvironment:'NNTPSERVER'.
+
+ sock := Socket newTCPclientToHost:host port:'nntp'.
+ Transcript showCR:sock nextLine.
+ sock buffered:false.
+
+ sock nextPutAll:'HELP'; cr.
+ [:exit |
+ |line|
+
+ line := sock nextLine.
+ line = '.' ifTrue:[exit value:nil].
+ Transcript showCR:line.
+ ] loopWithExit.
+ sock close
+ [exEnd]
example (connect to finger daemon, get users entry):
- [exBegin]
- |sock host entry|
-
- host := OperatingSystem getHostName.
-
- sock := Socket newTCPclientToHost:host port:'finger'.
- sock isNil ifTrue:[
- self warn:'no finger daemon is running'.
- ^ self
- ].
- sock useCRLF:true.
- sock buffered:false.
- sock isNil ifTrue:[
- Transcript showCR:'cannot connect to local finger daemon'
- ] ifFalse:[
- sock nextPutAll:(OperatingSystem getLoginName).
- sock cr.
-
- entry := sock nextLine.
- Transcript showCR:entry.
-
- sock close
- ]
- [exEnd]
+ [exBegin]
+ |sock host entry|
+
+ host := OperatingSystem getHostName.
+
+ sock := Socket newTCPclientToHost:host port:'finger'.
+ sock isNil ifTrue:[
+ self warn:'no finger daemon is running'.
+ ^ self
+ ].
+ sock useCRLF:true.
+ sock buffered:false.
+ sock isNil ifTrue:[
+ Transcript showCR:'cannot connect to local finger daemon'
+ ] ifFalse:[
+ sock nextPutAll:(OperatingSystem getLoginName).
+ sock cr.
+
+ entry := sock nextLine.
+ Transcript showCR:entry.
+
+ sock close
+ ]
+ [exEnd]
example (connect to an ftp server):
- [exBegin]
- |sock host|
-
- host := OperatingSystem getHostName.
- sock := Socket newTCPclientToHost:host port:'ftp'.
-
- sock buffered:false.
- Transcript showCR:sock nextLine.
- sock nextPutAll:('USER ' , 'anonymous'); cr.
- Transcript showCR:sock nextLine.
- sock nextPutAll:('PASS ' , 'fooBar'); cr.
- Transcript showCR:sock nextLine.
- sock nextPutAll:'LIST'; cr.
- Transcript showCR:sock nextLine.
- sock close.
-
- 'dont know enough of the ftp protocol to continue here ...'
- [exEnd]
+ [exBegin]
+ |sock host|
+
+ host := OperatingSystem getHostName.
+ sock := Socket newTCPclientToHost:host port:'ftp'.
+
+ sock buffered:false.
+ Transcript showCR:sock nextLine.
+ sock nextPutAll:('USER ' , 'anonymous'); cr.
+ Transcript showCR:sock nextLine.
+ sock nextPutAll:('PASS ' , 'fooBar'); cr.
+ Transcript showCR:sock nextLine.
+ sock nextPutAll:'LIST'; cr.
+ Transcript showCR:sock nextLine.
+ sock close.
+
+ 'dont know enough of the ftp protocol to continue here ...'
+ [exEnd]
example (connect to an snmp server [UDP]):
- [exBegin]
- |sock port|
-
- sock := Socket newUDP.
- port := Socket portOfService:'snmp'.
- sock connectTo:(OperatingSystem getHostName) port:port.
- sock buffered:false.
- Transcript showCR:'got it'.
- sock close.
- [exEnd]
+ [exBegin]
+ |sock port|
+
+ sock := Socket newUDP.
+ port := Socket portOfService:'snmp'.
+ sock connectTo:(OperatingSystem getHostName) port:port.
+ sock buffered:false.
+ Transcript showCR:'got it'.
+ sock close.
+ [exEnd]
example (await connection from a client and read some data):
- |connectSock sock|
-
- connectSock := Socket newTCPserverAtPort:9998.
- connectSock isNil ifTrue:[
- Transcript showCR:'socket setup failed.'.
- ] ifFalse:[
- Transcript showCR:'listen ..'.
- (connectSock listenFor:5) ifFalse:[
- Transcript showCR:'listen failed.'.
- ] ifTrue:[
- Transcript showCR:'wait'.
- connectSock readWait.
- Transcript showCR:'accept'.
- sock := connectSock accept.
- sock isNil ifTrue:[
- Transcript showCR:'accept failed.'.
- ] ifFalse:[
- sock buffered:false.
- Transcript showCR:'server: got it'.
- 'can now do transfer via sock'.
- Transcript showCR:'read'.
- Transcript showCR:('got: ' , sock nextLine).
-
- Transcript showCR:'close'.
- sock close
- ].
- connectSock close.
- ]
- ]
+ [exBegin]
+ |connectSock sock|
+
+ connectSock := Socket newTCPserverAtPort:9998.
+ connectSock isNil ifTrue:[
+ Transcript showCR:'socket setup failed.'.
+ ] ifFalse:[
+ Transcript showCR:'listen ..'.
+ (connectSock listenFor:5) ifFalse:[
+ Transcript showCR:'listen failed.'.
+ ] ifTrue:[
+ Transcript showCR:'wait'.
+ connectSock readWait.
+ Transcript showCR:'accept'.
+ sock := connectSock accept.
+ sock isNil ifTrue:[
+ Transcript showCR:'accept failed.'.
+ ] ifFalse:[
+ sock buffered:false.
+ Transcript showCR:'server: got it'.
+ 'can now do transfer via sock'.
+ Transcript showCR:'read'.
+ Transcript showCR:('got: ' , sock nextLine).
+
+ Transcript showCR:'close'.
+ sock close
+ ].
+ connectSock close.
+ ]
+ ]
+ [exEnd]
example (connect to above server and send some data):
- |sock|
-
- sock := Socket newTCPclientToHost:(OperatingSystem getHostName) port:9998.
- sock isNil ifTrue:[
- Transcript showCR:'nope'
- ] ifFalse:[
- sock buffered:false.
- Transcript showCR:'client: got it'.
- 'can now do transfer via sock'.
- Transcript showCR:'sending <hello>'.
- sock nextPutLine:'hello'.
- sock close
- ]
+ [exBegin]
+ |sock|
+
+ sock := Socket newTCPclientToHost:(OperatingSystem getHostName) port:9998.
+ sock isNil ifTrue:[
+ Transcript showCR:'nope'
+ ] ifFalse:[
+ sock buffered:false.
+ Transcript showCR:'client: got it'.
+ 'can now do transfer via sock'.
+ Transcript showCR:'sending <hello>'.
+ sock nextPutLine:'hello'.
+ sock close
+ ]
+ [exEnd]
example: UNIX domain socket (await connection from a client and read some data):
-
- |connectSock sock|
-
- '/tmp/ud_socket' asFilename remove.
- connectSock := Socket newUNIXserverAt:'/tmp/ud_socket'.
- connectSock isNil ifTrue:[
- Transcript showCR:'socket setup failed.'.
- ] ifFalse:[
- Transcript showCR:'listen ..'.
- (connectSock listenFor:5) ifFalse:[
- Transcript showCR:'listen failed.'.
- ] ifTrue:[
- Transcript showCR:'wait'.
- connectSock buffered:false.
- connectSock readWait.
- Transcript showCR:'accept'.
- sock := connectSock accept.
- sock isNil ifTrue:[
- Transcript showCR:'accept failed.'.
- ] ifFalse:[
- sock buffered:false.
- Transcript showCR:'server: got it'.
- 'can now do transfer via sock'.
- Transcript showCR:'read'.
- Transcript showCR:('got: ' , sock nextLine).
-
- Transcript showCR:'close'.
- sock close
- ].
- connectSock close.
- ]
- ]
+ [exBegin]
+ |connectSock sock|
+
+ '/tmp/ud_socket' asFilename remove.
+ connectSock := Socket newUNIXserverAt:'/tmp/ud_socket'.
+ connectSock isNil ifTrue:[
+ Transcript showCR:'socket setup failed.'.
+ ] ifFalse:[
+ Transcript showCR:'listen ..'.
+ (connectSock listenFor:5) ifFalse:[
+ Transcript showCR:'listen failed.'.
+ ] ifTrue:[
+ Transcript showCR:'wait'.
+ connectSock buffered:false.
+ connectSock readWait.
+ Transcript showCR:'accept'.
+ sock := connectSock accept.
+ sock isNil ifTrue:[
+ Transcript showCR:'accept failed.'.
+ ] ifFalse:[
+ sock buffered:false.
+ Transcript showCR:'server: got it'.
+ 'can now do transfer via sock'.
+ Transcript showCR:'read'.
+ Transcript showCR:('got: ' , sock nextLine).
+
+ Transcript showCR:'close'.
+ sock close
+ ].
+ connectSock close.
+ ]
+ ]
+ [exEnd]
example (connect to above server and send some data;
- Notice, this fails, if above server code is executed in the same ST/X image
- (at least on LINUX), since the OS does not correctly handle
- a connect from within an interrupted accept system call
- On SGI's SVR4, this works ok
-
- |sock|
-
- sock := Socket newUNIXclientTo:'/tmp/ud_socket'.
- sock isNil ifTrue:[
- Transcript showCR:'nope'
- ] ifFalse:[
- sock buffered:false.
- Transcript showCR:'client: got it'.
- 'can now do transfer via sock'.
- Transcript showCR:'sending <hello>'.
- sock nextPutLine:'hello'.
- sock close
- ]
-
+ Notice, this fails, if above server code is executed in the same ST/X image
+ (at least on LINUX), since the OS does not correctly handle
+ a connect from within an interrupted accept system call
+ On SGI's SVR4, this works ok
+ [exBegin]
+ |sock|
+
+ sock := Socket newUNIXclientTo:'/tmp/ud_socket'.
+ sock isNil ifTrue:[
+ Transcript showCR:'nope'
+ ] ifFalse:[
+ sock buffered:false.
+ Transcript showCR:'client: got it'.
+ 'can now do transfer via sock'.
+ Transcript showCR:'sending <hello>'.
+ sock nextPutLine:'hello'.
+ sock close
+ ]
+ [exEnd]
+
+
+ example (UDP await packet from a client and read some data):
+ [exBegin]
+ |udpSock sock addr n dataBuffer|
+
+ udpSock := Socket newUDPserverAtPort:9999.
+ udpSock isNil ifTrue:[
+ Transcript showCR:'socket setup failed.'.
+ ] ifFalse:[
+ Transcript showCR:'wait'.
+ udpSock readWait.
+
+ addr := IPSocketAddress new.
+ dataBuffer := ByteArray new:1000.
+ n := udpSock receiveFrom:addr buffer:dataBuffer start:1 for:dataBuffer size.
+ n > 0 ifTrue:[
+ Transcript showCR:('got: ' , n printString , 'bytes from ' , addr printString).
+ Transcript showCR:('data: ' , (dataBuffer copyTo:n) printString).
+ ] ifFalse:[
+ Transcript showCR:'read failed'.
+ ].
+
+ Transcript showCR:'close'.
+ udpSock close
+ ]
+ [exEnd]
+ example (connect to above UDP server and send some data;
+ [exBegin]
+ |sock|
+
+ sock := Socket newUDP.
+ sock isNil ifTrue:[
+ Transcript showCR:'nope'
+ ] ifFalse:[
+ sock sendTo:(IPSocketAddress new hostName:'localhost' port:9999) buffer:'hello world'.
+ sock close
+ ]
+ [exEnd]
example: pingWalk (try to ping hosts on the local network)
- [exBegin]
- |myName myAddress list top hosts walkProcess port|
-
- myName := OperatingSystem getHostName.
- myAddress := Socket ipAddressOfHost:myName.
-
- port := Socket portOfService:'echo'.
- port isNil ifTrue:[
- self error:'dont know echo port'.
- ^ self
- ].
-
- top := StandardSystemView new.
- top label:'PING net walk'.
-
- list := ScrollableView for:ListView in:top.
- list origin:0.0@0.0 corner:1.0@1.0.
-
- top openAndWait.
-
- walkProcess := [
- |l low hi direction tryHostID dottedName hostName conn addr|
-
- l := SortedCollection new.
-
- ' only works with type C-net
- the code below could simply do 1 to:254 do:[:hostID }
- but, to probe likely hosts earlier, the probing is done
- ping-pong like around my ip-address (assuming, that other machines
- have numbers around my own)'.
-
- low := hi := (myAddress at:4).
- direction := 1.
-
- [low > 0 or:[hi < 255]] whileTrue:[
- direction > 0 ifTrue:[
- hi := hi + 1.
- tryHostID := hi.
- direction := -1.
- ] ifFalse:[
- low := low - 1.
- tryHostID := low.
- direction := 1.
- ].
- (tryHostID between:1 and:254) ifTrue:[
- dottedName := (myAddress at:1) printString
- , '.' , (myAddress at:2) printString
- , '.' , (myAddress at:3) printString
- , '.' , tryHostID printString.
-
- top label:'PING net walk - trying ' , dottedName.
-
- top windowGroup withCursor:Cursor wait do:[
- conn := Socket newTCPclientToHost:dottedName port:port withTimeout:1000.
- conn notNil ifTrue:[
- addr := Socket ipAddressOfHost:dottedName.
- hostName := Socket hostWithIpAddress:addr.
- hostName isNil ifTrue:[
- hostName :='?'
- ].
- l add:(dottedName paddedTo:15 with:Character space)
- , ' '
- , (hostName paddedTo:15 with:Character space)
- , ' up & reachable'.
- list list:l.
- conn close.
- ]
- ].
- ].
- ].
- top label:'PING reachable hosts'.
- ] forkAt:(Processor userBackgroundPriority).
- walkProcess name:'ping net walker'.
- [exEnd]
-
-
- This example creates a simple UDP server that accepts
- single packets from anybody and broadcasts them to all
- clients that have connected so far.
-
- [exBegin]
- | socket address buffer msgSize clients |
- clients := Set new.
- address := IPSocketAddress new.
- buffer := String new: 1024.
-
- socket := self newUDPserverAtPort: 6666.
-
- Transcript showCR: 'server starting'.
-
- [
- [true] whileTrue: [
- (socket readWaitWithTimeoutMs: 200) ifFalse: [
- msgSize := socket
- receiveFrom: address
- buffer: buffer
- start: 1
- for: buffer size.
-
- clients add: address copy.
- clients do: [ :clientAddress |
- socket
- sendTo: clientAddress
- buffer: buffer
- start: 1
- for: msgSize]]
- ]
- ] valueNowOrOnUnwindDo:[
- Transcript showCR: 'server shutting down'.
- socket close
- ]
- [exEnd]
+ [exBegin]
+ |myName myAddress list top hosts walkProcess port|
+
+ myName := OperatingSystem getHostName.
+ myAddress := Socket ipAddressOfHost:myName.
+
+ port := Socket portOfService:'echo'.
+ port isNil ifTrue:[
+ self error:'dont know echo port'.
+ ^ self
+ ].
+
+ top := StandardSystemView new.
+ top label:'PING net walk'.
+
+ list := ScrollableView for:ListView in:top.
+ list origin:0.0@0.0 corner:1.0@1.0.
+
+ top openAndWait.
+
+ walkProcess := [
+ |l low hi direction tryHostID dottedName hostName conn addr|
+
+ l := SortedCollection new.
+
+ ' only works with type C-net
+ the code below could simply do 1 to:254 do:[:hostID }
+ but, to probe likely hosts earlier, the probing is done
+ ping-pong like around my ip-address (assuming, that other machines
+ have numbers around my own)'.
+
+ low := hi := (myAddress at:4).
+ direction := 1.
+
+ [low > 0 or:[hi < 255]] whileTrue:[
+ direction > 0 ifTrue:[
+ hi := hi + 1.
+ tryHostID := hi.
+ direction := -1.
+ ] ifFalse:[
+ low := low - 1.
+ tryHostID := low.
+ direction := 1.
+ ].
+ (tryHostID between:1 and:254) ifTrue:[
+ dottedName := (myAddress at:1) printString
+ , '.' , (myAddress at:2) printString
+ , '.' , (myAddress at:3) printString
+ , '.' , tryHostID printString.
+
+ top label:'PING net walk - trying ' , dottedName.
+
+ top windowGroup withCursor:Cursor wait do:[
+ conn := Socket newTCPclientToHost:dottedName port:port withTimeout:1000.
+ conn notNil ifTrue:[
+ addr := Socket ipAddressOfHost:dottedName.
+ hostName := Socket hostWithIpAddress:addr.
+ hostName isNil ifTrue:[
+ hostName :='?'
+ ].
+ l add:(dottedName paddedTo:15 with:Character space)
+ , ' '
+ , (hostName paddedTo:15 with:Character space)
+ , ' up & reachable'.
+ list list:l.
+ conn close.
+ ]
+ ].
+ ].
+ ].
+ top label:'PING reachable hosts'.
+ ] forkAt:(Processor userBackgroundPriority).
+ walkProcess name:'ping net walker'.
+ [exEnd]
+
+
+ This example creates a simple UDP server that accepts
+ single packets from anybody and broadcasts them to all
+ clients that have connected so far.
+
+ [exBegin]
+ | socket address buffer msgSize clients |
+ clients := Set new.
+ address := IPSocketAddress new.
+ buffer := String new: 1024.
+
+ socket := self newUDPserverAtPort: 6666.
+
+ Transcript showCR: 'server starting'.
+
+ [
+ [true] whileTrue: [
+ (socket readWaitWithTimeoutMs: 200) ifFalse: [
+ msgSize := socket
+ receiveFrom: address
+ buffer: buffer
+ start: 1
+ for: buffer size.
+
+ clients add: address copy.
+ clients do: [ :clientAddress |
+ socket
+ sendTo: clientAddress
+ buffer: buffer
+ start: 1
+ for: msgSize]]
+ ]
+ ] valueNowOrOnUnwindDo:[
+ Transcript showCR: 'server shutting down'.
+ socket close
+ ]
+ [exEnd]
send a datagram to above server:
- [exBegin]
-
- | socket address buffer host msg |
-
- host := Dialog
- request: 'What is the name of the server''s host?'
- initialAnswer: 'localhost'.
-
- socket := self newUDP.
-
- address := IPSocketAddress hostName: host port: 6666.
-
- buffer := ByteArray new: 1000.
- [
- [(msg := Dialog request: 'Say something') isEmpty] whileFalse:[
- | replySize stream |
-
- socket writeWait.
- stream := buffer writeStream.
- stream nextPutAll: msg.
- socket sendTo:address buffer:buffer start:1 for:stream position.
- socket readWait.
-
- replySize := socket receiveFrom:address buffer:buffer.
- replySize > 0 ifTrue: [
- Transcript cr; nextPutAll: 'Server acknowledged: '.
- Transcript show: ((buffer copyFrom: 1 to: replySize) asString)
- ]
- ]
- ] valueNowOrOnUnwindDo: [socket close].
- Transcript cr
- [exEnd]
+ [exBegin]
+
+ | socket address buffer host msg |
+
+ host := Dialog
+ request: 'What is the name of the server''s host?'
+ initialAnswer: 'localhost'.
+
+ socket := self newUDP.
+
+ address := IPSocketAddress hostName: host port: 6666.
+
+ buffer := ByteArray new: 1000.
+ [
+ [(msg := Dialog request: 'Say something') isEmpty] whileFalse:[
+ | replySize stream |
+
+ socket writeWait.
+ stream := buffer writeStream.
+ stream nextPutAll: msg.
+ socket sendTo:address buffer:buffer start:1 for:stream position.
+ socket readWait.
+
+ replySize := socket receiveFrom:address buffer:buffer.
+ replySize > 0 ifTrue: [
+ Transcript cr; nextPutAll: 'Server acknowledged: '.
+ Transcript show: ((buffer copyFrom: 1 to: replySize) asString)
+ ]
+ ]
+ ] valueNowOrOnUnwindDo: [socket close].
+ Transcript cr
+ [exEnd]
"
-
! !
!Socket class methodsFor:'Compatibility ST80'!
@@ -4977,5 +5020,5 @@
!Socket class methodsFor:'documentation'!
version
- ^ '$Header: /cvs/stx/stx/libbasic2/Socket.st,v 1.157 2002-01-10 13:47:27 cg Exp $'
+ ^ '$Header: /cvs/stx/stx/libbasic2/Socket.st,v 1.158 2002-01-28 14:29:28 cg Exp $'
! !