|
Feed Post Category Post Date Article Structure Sites mentioned
php.net Next Article Previous Article |
Fsockopen Power PlaysSource: http://feeds.askapache.com/~r/apache/htaccess/~3/3...Displaying mentions in this article, for full text please visit source.
In unix you can send anything to the /dev/null device, for windoze think Recycle Bin, and likewise you can send anything to a socket created with fsockopen. I’ve seen fsockopen code that sends custom exploits to cisco routers, including being used by the metasploit framework. I’ve seen fsockopen telnet emulation, smtp/pop3 login, and a lot of other advanced raw networking that is exciting for me see. Some Definitions for Fsockopen client A program that establishes connections for the purpose of sending requests. server An application program that accepts connections in order to service requests by sending back responses. Simple Socket ExplantionA web server host listens on TCP port 80. When a client host wishes to view a resource on the web server, it establishes a TCP connection with the server host by opening a socket to send the request for the resource. When the connection is established, the client and server exchange requests and responses (respectively) until the connection is closed or aborted. HTTP and fsockopen
Here are some BOSS fsockopen functions I hacked together yesterday for use in my AskApache Crazy Cache WordPress Plugin. I’ve used code and ideas from 100’s of authors, projects, and docs to try to make this the very best I can. IntroThis is a working example employing as many of the best-practices, tips, and tricks for using fsockopen on remote streams that I could find. 100megs */ function askapache_txrx($fp,$request,$chunk=1024){ $rec=$buf=''; if(!@fwrite($fp, $request, strlen($request)))die('fwrite error'); while ( !@feof($fp) && askapache_time_ok(askapache_time_passed())){ $buf = @fread($fp, $chunk); $rec .= $buf; } if(!@fclose($fp))die('fclose error'); return $rec; } /* initiates the socket and download for the passed url. automatically handles gzip, chunked, both, and plain downloads. uses the long2ip/ip2long for ip validation, uses gethostbyname to get the ipv4 address which saves fsockopen from having to do the lookup final data is saved to $rbody but currently only displays headers.*/ function aa_dl($url=NULL){ global $aa_time; $ub = @parse_url($url); if(!isset($ub['host'])||empty($ub['host'])) die("bad url $url"); $proto = ($ub['scheme']=='https')?'ssl://':''; $port = (isset($ub['port'])&&!empty($ub['port'])) ? $ub['port']:($proto!='')?443:80; $path = (isset($ub['path'])&&!empty($ub['path'])) ? $ub['path']:'/'; $query = (isset($ub['query'])&&!empty($ub['query'])) ? '?'.$ub['query'] : ''; $host = $ub['host']; $ipp = @gethostbyname($host); $ip = ($ipp!=$host) ? long2ip(ip2long($ipp)) : $host; $headers=array( "GET {$path}{$query} HTTP/1.1", "Host: {$host}", 'User-Agent: Mozilla/5.0 (AskApache/; +http://www.askapache.com/)', 'Accept: text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,*/*;q=0.5', 'Accept-Language: en-us,en;q=0.5', 'Accept-Encoding: gzip,deflate', 'Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7', 'Connection: close','Referer: http://www.askapache.com' ); $request=join(AA_LF,$headers).AA_LF.AA_LF; $fp=askapache_get_sock($proto.$ip, $port); if($fp){ $rbody=$rec='';$resp_headers=array(); $rec=askapache_txrx($fp,$request); list($resp_headers, $rbody) = explode(AA_LF.AA_LF, trim($rec), 2); echo "n$request n$resp_headers n"; $gzip2=(stripos($resp_headers,'Content-Encoding')!==false && stripos($resp_headers,'gzip')!==false)?1:0; $chunk=(stripos($resp_headers,'Transfer-Encoding')!==false && stripos($resp_headers,'chunked')!==false)?1:0; $rbody=aa_decode_body($rbody,$chunk,$gzip2); unset($rbody); } } /* based on http://us.php.net/manual/en/function.fsockopen.php#75175 ungzips and/or re-assembles transfer-encoded:chunked responses returns the good response on success */ function aa_decode_body ($str, $chunked, $gzipped){ if($gzipped && !$chunked) return aa_gzdecode($str); if(!$gzipped && !$chunked) return $str; $tmp = $str; $str = ''; do { $tmp = ltrim($tmp); $pos = strpos($tmp,AA_LF); $len = hexdec(substr($tmp, 0, $pos)); if($gzipped) $str .= gzinflate(substr($tmp,($pos+12),$len)); else $str .=substr($tmp,($pos+2),$len); $tmp = substr($tmp,($len+$pos+2)); $chk=trim($tmp); } while (!empty($chk)); return $str; } /* based on http://us2.php.net/manual/en/function.gzencode.php#82520 saves the gzipped data to a tempfile, then outputs the decoded data to the output buffer using readgzfile, returning the decoded buffer and deleting the tempfile on success */ function aa_gzdecode($data){ $g=tempnam('/tmp','ff'); @file_put_contents($g,$data); ob_start(); readgzfile($g); $d=ob_get_clean(); @unlink($g); return $d; } /* very cool! this is run during socket reads and checks whether the script execution time limit or the socket read time limit has been met, killing the script if so, otherwise returns true. Run with a cron-like process */ function askapache_time_ok($sock_time=0) { global $aa_time; if (time()-$aa_time>AA_MAX_TIME) die('killed script.. time exceeded '.AA_MAX_TIME.' Total: '.$total); if ($sock_time>AA_RECV_TIME) die('Killed socket.. time exceeded '.AA_RECV_TIME.' Total: '.$sock_time); return true; } /* input for askapache_time_ok to keep track of each socket read time time. */ function askapache_time_passed() { global $aa_time_start; return (time() - $aa_time_start); } /* handles fsockopen errors, printing them out though you may want to die on err */ function askapache_sock_strerror($errno,$errstr){ switch($errno){ case -3: $err="Socket creation failed"; break; case -4: $err="DNS lookup failure"; break; case -5: $err="Connection refused or timed out"; break; case 111: $err="Connection refused"; break; case 113: $err="No route to host"; break; case 110: $err="Connection timed out"; break; case 104: $err="Connection reset by client"; break; default: $err="Connection failed"; break; } echo 'Fsockopen failed!'."n[".$errno."] ".$err." (".$errstr.") "; return false; } ?>Debugging Fsockopen If you really want to know more about fsockopen, you can do what I did and read all the relevant php source files, your OS sys, lib, and user files relevant to fsockopen, and of course you can always trace php using the fsockopen function to get an under-the-hood look at what in the world fsockopen is doing. Personally, I was trying to find more error codes and error strings to display when an fsockopen call failed, and I ended up finding over 50.. Tracing fsockopen using StraceOnce you save the above file on your site, you can use the strace tool to debug it. This is a tad overboard but way cool nevertheless! strace -e trace=connect php -nef fsockopen-test.php connect(3, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("66.33.216.129")}, 28) = 0 connect(3, {sa_family=AF_INET, sin_port=htons(80), sin_addr=inet_addr("192.87.106.226")}, 16) = -1 EINPROGRESS (Operation now in progress)strace -e trace=network php -nef fsockopen-test.php socket(PF_FILE, SOCK_STREAM, 0) = 3 connect(3, {sa_family=AF_FILE, path="/var/run/.nscd_socket"}, 110) = -1 ENOENT (No such file or directory) socket(PF_INET, SOCK_DGRAM, IPPROTO_IP) = 3 connect(3, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("66.33.216.129")}, 28) = 0 send(3, "2742211 1 5httpd6apache3org 1"..., 34, 0) = 34 recvfrom(3, "274221201200 1 1 5httpd6apache3org "..., 1024, 0, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("66.33.216.129")}, [16]) = 50 socket(PF_INET6, SOCK_DGRAM, IPPROTO_IP) = -1 EAFNOSUPPORT (Address family not supported by protocol) socket(PF_INET, SOCK_STREAM, IPPROTO_IP) = 3 connect(3, {sa_family=AF_INET, sin_port=htons(80), sin_addr=inet_addr("192.87.106.226")}, 16) = -1 EINPROGRESS (Operation now in progress) getsockopt(3, SOL_SOCKET, SO_ERROR, [0], [4]) = 0 send(3, "GET / HTTP/1.1rnHost: httpd.apac"..., 356, MSG_DONTWAIT) = 356 recv(3, "HTTP/1.1 200 OKrnDate: Wed, 02 J"..., 8192, MSG_DONTWAIT) = 2609 recv(3, "", 8192, MSG_DONTWAIT) = 0strace -q -e trace=all php -nef fsockopen-test.php mmap2(NULL, 266240, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb76ba000 munmap(0xb76ba000, 266240) = 0 socket(PF_FILE, SOCK_STREAM, 0) = 3 connect(3, {sa_family=AF_FILE, path="/var/run/.nscd_socket"}, 110) = -1 ENOENT (No such file or directory) close(3) = 0 open("/etc/hosts", O_RDONLY) = 3 fcntl64(3, F_GETFD) = 0 fcntl64(3, F_SETFD, FD_CLOEXEC) = 0 fstat64(3, {st_mode=S_IFREG|0644, st_size=948, ...}) = 0 mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7f6e000 read(3, "# /etc/hosts - dh2 generatedn127"..., 4096) = 948 read(3, "", 4096) = 0 close(3) = 0 munmap(0xb7f6e000, 4096) = 0 socket(PF_INET, SOCK_DGRAM, IPPROTO_IP) = 3 connect(3, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("66.33.216.129")}, 28) = 0 send(3, "X~1 1 2entwikipedia3org 1"..., 34, 0) = 34 gettimeofday({1214998196, 656179}, NULL) = 0 poll([{fd=3, events=POLLIN, revents=POLLIN}], 1, 5000) = 1 ioctl(3, FIONREAD, [100]) = 0 recvfrom(3, "X~201200 1 3 2entwikipedia3org 1"..., 1024, 0, {sa_family=AF_INET, sin_port=htons(53), sin_addr=inet_addr("66.33.216.129")}, [16]) = 100 close(3) = 0 time(NULL) = 1214998196 gettimeofday({1214998196, 656754}, NULL) = 0 socket(PF_INET, SOCK_STREAM, IPPROTO_IP) = 3 fcntl64(3, F_GETFL) = 0×2 (flags O_RDWR) fcntl64(3, F_SETFL, O_RDWR|O_NONBLOCK) = 0 connect(3, {sa_family=AF_INET, sin_port=htons(80), sin_addr=inet_addr("208.80.152.2")}, 16) = -1 EINPROGRESS (Operation now in progress) poll([{fd=3, events=POLLIN|POLLOUT|POLLERR|POLLHUP, revents=POLLOUT}], 1, 10000) = 1 getsockopt(3, SOL_SOCKET, SO_ERROR, [0], [4]) = 0 fcntl64(3, F_SETFL, O_RDWR) = 0 send(3, "GET /wiki/Main_Page HTTP/1.1rnHo"..., 370, MSG_DONTWAIT) = 370 poll([{fd=3, events=POLLIN|POLLPRI|POLLERR|POLLHUP}], 1, 0) = 0 time(NULL) = 1214998196 poll([{fd=3, events=POLLIN|POLLERR|POLLHUP, revents=POLLIN}], 1, 30000) = 1 recv(3, "HTTP/1.0 200 OKrnDate: Wed, 02 J"..., 8192, MSG_DONTWAIT) = 2896 time(NULL) = 1214998196 poll([{fd=3, events=POLLIN|POLLERR|POLLHUP, revents=POLLIN}], 1, 30000) = 1 recv(3, "214!337i30733623w253wy21526EL227;227253261"..., 8192, MSG_DONTWAIT) = 5792 time(NULL) = 1214998196 poll([{fd=3, events=POLLIN|POLLERR|POLLHUP, revents=POLLIN}], 1, 30000) = 1 recv(3, "420127321417yI347257371373344332330227245"..., 8192, MSG_DONTWAIT) = 7487 time(NULL) = 1214998197 poll([{fd=3, events=POLLIN|POLLERR|POLLHUP, revents=POLLIN}], 1, 30000) = 1 recv(3, "", 8192, MSG_DONTWAIT) = 0 close(3) = 0 write(1, "nGET /wiki/Main_Page HTTP/1"..., 1300
From the FreeBSD man page for socket(2) Sockets of type SOCK_STREAM are full-duplex byte streams, similar to pipes. A stream socket must be in a connected state before any data may be sent or received on it. A connection to another socket is created with a connect(2) system call. Once connected, data may be transferred using read(2) and write(2) calls or some variant of the send(2) and recv(2) functions. (Some protocol families, such as the Internet family, support the notion of an ``implied connect'', which permits data to be sent piggybacked onto a connect operation by using the sendto(2) system call.) When a session has been completed a close(2) may be performed. Out-of-band data may also be transmitted as described in send(2) and received as described in recv(2). The communications protocols used to implement a SOCK_STREAM insure that data is not lost or duplicated. If a piece of data for which the peer protocol has buffer space cannot be successfully transmitted within a reasonable length of time, then the connection is considered broken and calls will indicate an error with -1 returns and with ETIMEDOUT as the specific code in the global variable errno. The protocols optionally keep sockets ``warm'' by forcing transmissions roughly every minute in the absence of other activity. An error is then indicated if no response can be elicited on an otherwise idle connection for an extended period (e.g. 5 minutes). A SIGPIPE signal is raised if a process sends on a broken stream; this causes naive processes, which do not handle the sig- nal, to exit. Random PostsFeeds and posts are not affliated with ://URLFAN. They are displayed here simply for informational purposes, if you would like to remove your feed, posts, or domain from ranking and analysis, please contact us. |
://URLFAN (.15)
Contact Us - About ://URLFAN - Notify me when my site is added or updated.


