There are two (or more) computers on LAN with internet access.
They have the same:
operating system,
browser and browser version,
user name.
They are visiting my webpage which can use js and php to retrive informations.
Is there any way I can find differences between these clients with retrived information?
Which informations are different?
Set a (random valued) cookie or a session.
The two machines will have unique identities.
Their IP addresses would be different, unless they're using a proxy and/or NAT firewall. That information can be retrieved trivially via $_SERVER['REMOTE_ADDR']. There may an X-Forwarded-For header that some proxies might put in place, revealing the internal address, but it's not guaranteed to be there, and definitely not guaranteed to be reliable.
There's a few client-side tricks you can use to get machine's local address, but again, if they're behind a NAT firewall and/or proxy, there's no guaranteed that both machines aren't on two seperate networks and both coincidentally have the same private IP address.
Related
I have website and have one page for receiving some news (newly registered users, activity, etc.) and is restricted for everyone except for my IP (Page for only me to view).
I'm interested if there is a way that someone else can "fake" my IP and view this file?
P.S. I am aware of other ways of doing this.
Usually, you dont get fixed IPs, most provider give dynamic IPs. So if you restart your Router, your IP will change and make it impossible to access the page again. If you get a fixed IP, it should work. He can ofc. modify the IP, but then he wont get the response back.
Converting my comments to an answer.
It depends on how you are trying to get the client's IP address. If you are:
only using $_SERVER['REMOTE_ADDR'] to get the ip address
don't have a shared ip address
don't use a (shared) proxy
You should be just fine, because a possible attacker can technically spoof the ip address, but that would not work because, (as Andrey) rightfully pointed out to me the tcp handshake would simply fail.
Some caveats:
Your IP may change at some point effectively locking yourself out.
When you are behind a proxy / internal -> external router / vpn / otherwise shared ip other people in the same network might also have access
Never ever ever use $_SERVER['HTTP_X_FORWARDED_FOR '] because this can be spoofed easily.
Is there a safe way, to identify a device which might be behind a Router (so the IP is not unique) in PHP?
Background: I have several embedded devices (self programmed & adaptable) which contact a webserver (php+mysql) with status updates. These updates are then - if the source is confirmed - saved to the database.
As I understand it $_SERVER['REMOTE_ADDR'] usually can be trusted (except some IIS configuration where it may - under special circumstances - wrongfully return 127.0.0.1; but different story)
Anyhow since I use SSL, the IP address really should not be a problem, because there a handshake is required and if the IP is faked or simply wrong, the connection should not be established
For now I require IP addresses to be whitelisted by admin, for an status update to be acceppted
The device additionally sends the MAC address via $_POST to identify the different modules with identical IP address (I know this can very easily be forged, and right now will be trusted if the IP address is trusted)
So first of all I am not sure if the IP address in itself is enough for it to be safe from attacks from the outside
Secondly if the device is behind a router, it will have the same IP address as every PC/device on that network. So about anyone there could forge a status update with a fake MAC address (simply as post variable), and since the IP address is whitelisted it will be trusted
So is there any way of confirming the identity of a device, or do you know a better way of doing this?
Aside: Going the other way, and have the webserver poll the different devices might be an option, but since there might be many (> 2000) devices of which we need the very last status (change) I thought it to be inefficient.
IP addresses can be spoofed, MAC addresses can be forged, so theses methods are not sufficient. The general approach is to assign a key to each client device (possibly the same key to all devices, even if this probably a bad idea). The "key" can be anything from a predefined string (weak, think username/password) to a signed certificate (strong, think SSL).
Both can be implemented either at the application level (by PHP) or at server level. If your application runs on Apache httpd server, I would rather recommend using its built-in features as it supports both approaches.
Is it possible to read out the NAT-Header of an IP-Package to identify the sending machine in php.
My goal is to identify on how many computers my users are logging in to my page.
Best regards
It's not possible to do - there are numerous routers between you and final user.
The NAT is organized using NAT Tables which are stored in routers memory, so there is no sensible information in the network packages. So it's not possible by definition.
Short answer: NO!
The server gets only the last public ip of the request, in the case of NAT, the ip of the router.
How to change ip address such that it does not reveal our original address when using $_SERVER['REMOTE_ADDR']; in php
You need to use a proxy server if you're trying to access a website from a different IP than your own. Wikipedia has more information.
There are several options I have in mind for this. I will go from the simpler to the more complicated one.
First, you could use a proxy server and ask him through an HTTP request made by your program or your browser, to fetch a resource for you. The proxy server will take the role of querying a resource in your place to the target service.
Example :
You want to retrieve the main page of the domain stackoverflow.com. You ask the proxy server to ask stackoverflow's HTTP server to send him the main page and he will forward it back to you.
To SO webserver, the superglobal $_SERVER['REMOTE_ADDR'] variable will correspond to the proxy server's IP address and not yours. However, the HTTP protocol implements some fields such as HTTP_VIA, HTTP_X_FORWARDED_FOR, or HTTP_FORWARDED which can be used to know if the current HTTP request is made by a proxy or not.
A transparent proxy will not specify those fields and will not modify your request whereas a non-transparent proxy may reveal the original IP address of the original requester. You got to use a reliable proxy which will act as you intends it to act. Another thing to consider is the use of an SSL tunnel between you and the proxy to avoid eavesdropping.
The second solution is to use a VPN (Virtual private network) server. It would be too complicated to fully explains how this works, but remember this, when you are connected to a computer using a VPN service (like l2tpd, pptpd ...) it's like you were on the same LAN with this computer. So you can transparently make requests to a webserver and he will never find out what's your real IP address.
A third solution could be to use linked nodes based network such as TOR. It's a free network you can connect to, and you will be completely anonymous to regular people. The TOR network power is to provide a network of many nodes and each nodes doesn't know anything about other nodes, so even people connected to the TOR network cannot know anything about you. I suggest you to read more about this if you're interested.
There are more complicated other solutions such as TCP session hijacking which is generally used to fake IP addresses and literally steal another computer's TCP connection, but this is out of the scope of this answer.
In writing a login module, I want to log IP's as an additional measure for verifying who's on the other side is still the same person on the other side.
I'm using $_SERVER['REMOTE_ADDR'] as one (of many) ways to get the remote machine's IP address. Aside from an IPv4 or IPv6 address, are there any other values i should expect this to return?
According to the PHP online documentation only an IP address should be returned.
http://us.php.net/manual/en/reserved.variables.server.php
“'REMOTE_ADDR':
The IP address from which the user is viewing the current page.”
The value can be an IPv4 or IPv6 address. Although you will probably only get canonical values be aware that IP addresses can be written in several ways. 192.0.2.1 is the same as 192.000.002.001, 2001:db8::1 is the same as 2001:0db0:0000:0000:0000:0000:0000:0001, etc. IPv4 addresses can even be written in IPv6 notation like ::ffff:192.0.2.1 or ::ffff:c000:0201 if the webserver accepts IPv4 connections on IPv6 sockets. I see that on Linux systems a lot.
Logging IP addresses should not be a problem as long as you reserve enough space. Actually using IP addresses for access control is getting more and more tricky these days. Because big parts of the world have run out of new IPv4 addresses you will see that ISPs have to use NAT on a large scale to keep connecting new customers to the IPv4 internet. These large scale NATs will use a pool of public IPv4 addresses for maybe thousands of customers. One IP address can be used by many customers, and one customer might end up using different addresses from the pool.
In IPv6 tracking the IP address has other things to take into account. The original IPv6 auto-configuration mechanism is based on using the MAC address as part of the IPv6 address. Because of privacy concerns most operating systems now use a (kind of) randomly generated interface identifier (usually the last 64 bits of the address) for outgoing connections, and those bits can/will can change over time. Some operating systems (Mac OS X) even keep statistics on whether IPv4 or IPv6 is faster and I have seen clients switch back and forth between IPv4 and IPv6 on occasion.
And then you can have users that roam from one wireless hotspot or office network to another, thereby switching IP addresses.
So I think logging IP addresses might make sense based on what you want to do with the data, but using them as (part of) a form of access control might cause more trouble than it's worth.
There's really no added security to checking IP addresses as these can be easily spoofed and anyone who's savvy enough to be intercepting POST transactions is probably doing this anyways.
Also, you may be potentially annoying legitimate users. Think of the instance where a person may be in a location where there are several free open wifi hotspots. When they get to your login page, they may be connected to one hotspot but by the time they sign in, their machine may have decided another router is a better option and therefore their IP will change. Believe it or not, this may deter some (albeit, very few) easily-frustrated users.
Honestly, I just wouldn't bother. Using SSL, if you can, is usually the best way to go to avoid security issues like the one you're describing. Good luck with your project.