计算机设备地理位置定位攻防原理调研 郝伟 2021/01/09 [TOC]
1. 1 需求说明
接入设备A连接网络后,攻击方B希望获得A的地理坐标信息(所在的经纬度或城市区域信息),A为了保护自己,希望能够实现以下两个层面的目标:
- 基本要求:让对方无法获得本机位置信息;
- 高级要求:让对方获得错误的本机位置信息。
为了实现此目标,我们首先需要了解一下设备定位技术的基本原理。
一般而言,可上网设备如果可以定位,都是通过硬件来实现,然后系统负责管理,软件层面负责调用,在调用的时候通常需要向系统申请一定的权限。在地理信息的获得,主要有以下四种方式,就此问题分别进行分析。
2. 2 GPS定位
2.1. 2.1 基本原理
GPS是英文Global Positioning System(全球定位系统)的简称。基本原理是与24颗近地轨道的GPS卫星中的至少3颗进行通信,利用通信时差计算所在位置。GPS卫星有两种专用的频率用于载波信号,即频率为1575.42MHz的L1载波和频率为1227.60MHz的L2载波。在L1和L2上又分别调制着多种信号,这些信号主要有:C/A码、P码和Y码。GPS定位功能现在已经被封装成芯片,即GPS定位芯片来完成。这些芯片的功能就是能够实现定位过程,通过API接口返回当前位置信息。
2.2. 2.2 硬件与精度
硬件支持:GPS定位芯片或硬件模块。 定位精度:1-100米,由模块性能决定。
2.3. 2.3 攻击方式
攻击方通过GPS获得接入设置的地理信息,只需获得用户的地址位置的访问权限即可获得,然后将设备的地理信息传回。
2.4. 2.4 防御方式
- 没有GPS设备无此问题,如一般的PC;
- 关闭GPS功能
- 对指定应用程序不开启的网络访问权限; 由于现在的常见系统都有对位置信息的保护,所以程序必需获得权限才可以访问。所以只要不给权限,程序则无法访问。实际上,在大多数计算机中,由于缺少GPS模块,都是无法获得数据的。
- 利用Hook修改系统数据 Hook的原理就是在应用程序调用系统函数时,通过在调用过程中的劫持,实现对返回数据的修改,从而使应用程序调用系统函数获得数据是Hook修改过的数据。关于Hook方法很多,如在Linux下可参见Linux下Hook方式汇总。
- 添加虚拟GPS模块 其原理类似于虚拟光驱,可以添加一个虚拟的GPS模块,从而返回虚拟的GPS地理信息。 参考资料:Virtual GPS, Fake Gps,虚拟gps定位。
3. 3 基站定位
3.1. 3.1 基本原理
使用4G/5G上网的基本原理是通过与附近的基站的数据传输,从而获得到附近基站的特征信息。由于基站几乎是不会变化的,所以只要获得了基站的特征信息,那么基本上接入方就在附近10公里内。
3.2. 3.2 硬件与精度
硬件支持:4G/5G芯片或硬件模块 定位精度:500m - 10km,取决于基站的强度,通常4G比5G的覆盖范围要大些。
3.3. 3.3 攻击方式
攻击方在获得相应权限后,即可通用使用通过GPS获得接入设置的地理信息,只需获得用户的地址位置的访问权限即可获得,然后将设备的地理信息传回。
举例来说,通过安装软件 TelephonyManager 获取基站信息,其格式lac:mcc:mnc:cell-id(基站信息)。通过附录1所示Android商代码,即可获得相关信息。代码运行后,即可得到以下基站的信息。
注意:代码运行需要 android.permission.ACCESS_COARSE_LOCATION 权限。
中国联通基站信息

中国移动基站信息

3.4. 3.4 防御原理
- 对于没有4G/5G模块的设备不存在此问题,如一般的PC;
- 对于有4G/5G模块的设备可以关闭4G/5G网络;
- 在开启4G/5G模块的设备上,不给相关应用开放网络访问权限,如
android.permission.ACCESS_COARSE_LOCATION。 - 通过系统层Hook(如Linux系统利用ptrace进行hook)修改获得的相关信息,但是不保存对不同版本的多种系统都生效。
4. 4 IP定位
4.1. 基本原理
IP地址实际上只是一个32位的二进制数,其本身并不能具备地理位置定位功能。但是由于公网的IP地址通常是比较固定的,很少发生变化,所以通过人工的方式建立字典,即可根据IP地址基本确定大概的位置。
4.2. 4.2 硬件与精度
硬件支持:以太网网卡 定位精度:建筑级,不过由于字典更新问题,可能失败或产生明显偏差。
4.3. 4.3 攻击方式
只需获得本机IP即可。通常是通过本机发另一台机器发一个消息包即可,只是一般接入设备都在内网,所以返回的IP地址通常为一个区域的出口IP。
4.4. 4.4 防御方式
F项目直接即可防御,因为返回的是攻击节点的IP地址。
5. 5 WIFI定位
5.1. 5.1 基本原理
WIFI定位的原理与IP地址类似,区别是Wifi定位使用的是无线AP的Mac地址:
- 每个无线AP都有一个全球唯一的MAC地址,且无线AP相对比较静态;
- 接入设备开启WiFi后,可以扫描并收集周围的AP信号,获得MAC信息,这里需要注意:无论无线AP是否加密,接入设备是否已连接,甚至信号强度不足以显示在无线信号列表中,都可以获取到AP广播出来的MAC地址。也就是说想要获得无线AP的MAC地址,只需要可以能够访问接入设备的网络连接功能即可。
- 通过位置字典,可以利用卫星定位的原理大概确定接入设备的地理位置;
5.2. 5.2 硬件与精度
硬件支持:无线网卡 定位精度:10-100米,视周边Wifi源数量和质量而定
5.3. 5.3 攻击方式
与4G/5G接入原理类似,通过获得网络接入权限,扫描周边Wifi的Mac并向攻击方返回,然后攻击方根据这些Mac地址,查询Mac地理信息字节,即可获得接入设备的大概地址位置。再次强调,在读取周边的无线AP时,是不需要任何认证的,所以能够非常轻易地获得周边无线AP的MAC信息。
5.4. 5.4 防御方式
- 不使用无线网络
- 对目标程序禁用网络信息读取权限
6. 结论
无论是使用GPS、4G/5G、还是使用Wifi都有较高的曝露风险。所以,推荐使用相对安全的方式是使用F项目的网络,以IP的方式来访问互联网。
如果一定要使用前三种方式,建议针对不同的系统进行相应的安全加固,具体加固的内涵有两点:
- 使得黑管程序无法获得访问地理信息数据的权限;
- 修改系统模块或函数使其获取的数据为虚假数据。
另外还要一点:即使黑客程序取得了数据需要返回,如果这些程序没有相应的数据发送权限,同时也能够保证接入设置的地理位置的安全。
7. 附录1:基站信息读取示例代码
package com.easipass.test;
import java.util.List;
import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.telephony.NeighboringCellInfo;
import android.telephony.TelephonyManager;
import android.telephony.cdma.CdmaCellLocation;
import android.telephony.gsm.GsmCellLocation;
import android.util.Log;
import android.view.View;
/**
* 功能描述:通过手机信号获取基站信息
* # 通过TelephonyManager 获取lac:mcc:mnc:cell-id
* # MCC,Mobile Country Code,移动国家代码(中国的为460);
* # MNC,Mobile Network Code,移动网络号码(中国移动为0,中国联通为1,中国电信为2);
* # LAC,Location Area Code,位置区域码;
* # CID,Cell Identity,基站编号;
* # BSSS,Base station signal strength,基站信号强度。
* @author android_ls
* 参考:https://blog.csdn.net/android_ls/article/details/8672442
*/
public class GSMCellLocationActivity extends Activity {
private static final String TAG = "GSMCellLocationActivity";
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// 获取基站信息
findViewById(R.id.button1).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
TelephonyManager mTelephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
// 返回值MCC + MNC
String operator = mTelephonyManager.getNetworkOperator();
int mcc = Integer.parseInt(operator.substring(0, 3));
int mnc = Integer.parseInt(operator.substring(3));
// 中国移动和中国联通获取LAC、CID的方式
GsmCellLocation location = (GsmCellLocation) mTelephonyManager.getCellLocation();
int lac = location.getLac();
int cellId = location.getCid();
Log.i(TAG, " MCC = " + mcc + "\t MNC = " + mnc + "\t LAC = " + lac + "\t CID = " + cellId);
// 中国电信获取LAC、CID的方式
/*CdmaCellLocation location1 = (CdmaCellLocation) mTelephonyManager.getCellLocation();
lac = location1.getNetworkId();
cellId = location1.getBaseStationId();
cellId /= 16;*/
// 获取邻区基站信息
List<NeighboringCellInfo> infos = mTelephonyManager.getNeighboringCellInfo();
StringBuffer sb = new StringBuffer("总数 : " + infos.size() + "\n");
for (NeighboringCellInfo info1 : infos) { // 根据邻区总数进行循环
sb.append(" LAC : " + info1.getLac()); // 取出当前邻区的LAC
sb.append(" CID : " + info1.getCid()); // 取出当前邻区的CID
sb.append(" BSSS : " + (-113 + 2 * info1.getRssi()) + "\n"); // 获取邻区基站信号强度
}
Log.i(TAG, " 获取邻区基站信息:" + sb.toString());
}
});
}
}