Talk about iOS identification virtual positioning research

Talk about iOS identification virtual positioning research

[[415572]]

This article is reprinted from the WeChat public account "Swift Community", the author is Jingfeng Lingyu. Please contact the Swift Community public account to reprint this article.

Preface

In recent business development, we have encountered the situation where the location of our project app was tampered, which was particularly obvious on the Android side. In order to prevent this kind of black industry from using virtual positioning to make money, iOS also has to circumvent virtual positioning.

After doing technical research, we found that it is difficult to achieve virtual positioning on an Apple phone with just a phone, but it is still possible. The bugly record of one of the company's project app reported that a user was using a jailbroken Apple phone, which really makes this behavior suspicious.

With the joint efforts of myself and my company partners, we have roughly investigated the following situations of using virtual positioning (the method of using Xcode virtual positioning is ignored in this article):

The first method: using a jailbroken phone

Generally, app users use jailbroken Apple phones. It can be inferred that the users are trying to take advantage of the system (there is also the possibility that their apps are reverse engineered by competing companies). This is because it is more difficult to buy a jailbroken phone than a normal one, and it is not as good as a normal phone in terms of system upgrades and use of the App Store. I have had some superficial knowledge of app reverse engineering by jailbreaking an iPhone 5s.

Identification method

It is recommended to use a one-size-fits-all approach, which is to identify whether the phone has Cydia.app installed. If it has, it will be directly judged as a jailbroken phone and report the "device abnormality" information to the backend. If you do not use this method, please continue reading, there will be other solutions later.

Professional reverse engineers can definitely avoid app developers from detecting Cydia installations. Of course, this is because the app is very popular in the market and is used by competitors for reverse analysis. In this case, virtual identification is basically meaningless. My personal suggestion is to directly lock and stop the interface service of this mobile app. Here is an article on how developers can identify whether an Apple phone has been jailbroken [1].

Code Implementation

  1. /// Determine whether it is a jailbroken device
  2. /// - Returns : true indicates the device is jailbroken
  3. func isBrokenDevice() -> Bool {
  4.      
  5. var isBroken = false  
  6.      
  7. let cydiaPath = "/Applications/Cydia.app"  
  8.      
  9. let aptPath = "/private/var/lib/apt"  
  10.      
  11. if FileManager. default .fileExists(atPath: cydiaPath) {
  12. isBroken = true  
  13. }
  14.      
  15. if FileManager. default .fileExists(atPath: aptPath) {
  16. isBroken = true  
  17. }
  18.      
  19. return isBroken
  20. }

The second method: Use Aisi Assistant

For scenarios where virtual positioning is used, it should mostly be drivers or docking personnel clocking in. In this scenario, a group of black industries that specialize in using virtual positioning to clock in and out may have emerged. For Apple phones, at present, the virtual positioning function of Aisi Assistant can be very well implemented.

Usage steps: Download the Aisi Assistant Mac client, connect the iPhone, click Virtual Positioning in the toolbox, select the location on the map, and then click Modify Virtual Positioning to modify the location information of the map.

Principle: On a non-jailbroken device, connect the computer and the phone via USB. The computer sends simulated coordinate data to the DTSimulateLocation service on the phone through a special protocol to achieve false positioning. Currently, the built-in location simulation in Xcode is achieved with the help of this technology. (Article source [2])

Identification method

1. By repeatedly recording the virtual positioning data of Aisi Assistant, it is found that the altitude of the longitude and latitude of its virtual positioning information is 0 and the number of longitude and latitude data bits is also worth studying. The real positioning and virtual positioning data are as follows:

True positioning

Virtual Positioning

By carefully observing the data, it is not difficult to find that if we compare the altitude of the positioning information and verify the double digits of the longitude and latitude, the black hat of virtual positioning can be easily cracked.

If we compare the virtual positioning height to 0, we will identify it as virtual positioning, and then a question will arise: the real altitude is the zero point. How to solve it? Here is a brief introduction to China's zero altitude position. China's zero point is located in the "People's Republic of China Zero Point" in Yinhai World on Donghai Middle Road, Qingdao. It is the only zero point in China. The only zero point.

At the same time, by comparing the double digits of longitude and latitude, it was found that the digits of virtual positioning were obviously wrong. By checking the digit precision of Swift's float and double, it was found that the longitude and latitude data of virtual positioning only perfunctorily met the double precision digits. The number of significant digits of Swift's float is 7, and the number of significant digits of double is 15.

Of course, the weight of this comparison is relatively low. I just updated the Aisi Assistant version and found that the new version has more detailed latitude and longitude, but it still does not reach the level of double significant digits. Compared with the current Aisi Assistant's height comparison recognition as virtual positioning, it is completely possible.

Code Implementation

  1. if location.altitude == 0.0 {
  2. print( "Virtual Positioning" )
  3. }
  4.  
  5. //The number of digits is used as the weight ratio for judgment. If the number of digits is less than 12 (the assumed value, the number of digits of this data of the virtual positioning of Aisi Assistant is 9 at present), it is judged as virtual positioning.
  6. // Dangerous, use with caution, but it is still OK as a record of small-weight abnormal data
  7. let longitude = location.coordinate.longitude
  8. let longitudeStr = "\(longitude)" .components(separatedBy: "." ). last ?? ""  
  9.  
  10. print( "Number of significant digits of longitude: \(longitudeStr.count)" )
  11. if longitudeStr.count < 12 {
  12.  
  13. print( "Virtual Positioning" )
  14. }

Second, upload the latitude and longitude of the positioned data to the backend, which then obtains detailed latitude and longitude information based on the received latitude and longitude, and makes an in-depth comparison of the driver's geographic information other than the latitude and longitude, giving priority to comparing the altitude, horizontalAccuracy, and verticalAccuracy values, and makes a decision after weighing whether the values ​​are equal.

three,

(1) By obtaining the public IP address, the approximate location can be obtained based on the IP address through the interface, but the error range is a bit large.

  1. //Get the public IP address
  2. var ipAddress: String? {
  3.  
  4. let ipUrl = URL(string: "https://ipof.in/txt" )!
  5. let ip = try? String.init(contentsOf: ipUrl, encoding: .utf8)
  6.  
  7. return ip
  8. }

(ii) Reading the app location via Wi-Fi hotspot[3]

(III) Use CLCircularRegion to set the specified longitude and latitude of the center of the region and the configurable radius for monitoring.

Simple code implementation:

  1. manager = CLLocationManager()
  2. //Set the location service manager proxy
  3. manager?.delegate = self
  4. //Set the positioning mode
  5. manager?.desiredAccuracy = kCLLocationAccuracyBest
  6. //Update distance
  7. manager?.distanceFilter = 100
  8. //Send authorization request
  9. manager?.requestWhenInUseAuthorization()
  10.  
  11. let latitude = 115.47560123242931
  12. let longitude = 29.9757535600194
  13. let centerCoordinate = CLLocationCoordinate2D(latitude: latitude, longitude: longitude)
  14. let locationIDStr = ""  
  15. let clRegion = CLCircularRegion(center: centerCoordinate, radius: 100, identifier: locationIDStr)
  16. manager?.startMonitoring( for : clRegion)
  17.  
  18. Proxy Methods
  19.  
  20. func locationManager(_ manager: CLLocationManager, didEnterRegion region: CLRegion) {
  21.  
  22. }
  23.  
  24. func locationManager(_ manager: CLLocationManager, didExitRegion region: CLRegion) {
  25.  
  26. }

(IV) Through IBeacon technology, use CBPeripheralManager under the CoreBluetooth framework to establish a Bluetooth base station. This positioning is end-to-end direct positioning, eliminating the need for GPS satellite and cellular data base station communication.

Simple code implementation:

  1. func locationManager(_ manager: CLLocationManager, didRangeBeacons beacons: [CLBeacon], in region: CLBeaconRegion) {
  2.  
  3. for beacon in beacons {
  4. var proximityStr: String = ""  
  5. switch beacon.proximity {
  6. case .far:
  7. proximityStr = "Unknown"  
  8. case .immediate:
  9. proximityStr = "Immediate"  
  10. case .near:
  11. proximityStr = "Near"  
  12. case .unknown:
  13. proximityStr = "Unknown"  
  14. }
  15.  
  16. var beaconStr = "Signal:" + beacon.proximityUUID.uuidString + "major:" + beacon.major.stringValue + "minor:" + beacon.minor.stringValue + "Distance:" + beacon.accuracy + "Signal:" + "\(Int64(beacon.rssi))" + "Proximity:" + proximityStr
  17.  
  18. print( "beacon information: \(beaconStr)" )
  19. }
  20.  
  21. }
  22.  
  23. func locationManager(_ manager: CLLocationManager, rangingBeaconsDidFailFor region: CLBeaconRegion, withError error: Error) {
  24.  
  25. }
  26.      
  27. -----------------------------------------------------------------------------------------------  
  28.  
  29. //You cannot create a class that complies with the CBPeripheralManagerDelegate protocol alone. You need to comply with the NSObjectProtocol protocol first. Here, you can directly inherit NSObject
  30. class CoreBluetoothManager:NSObject, CBPeripheralManagerDelegate {
  31.      
  32. //Build a Bluetooth base station.
  33. lazy var peripheralManager: CBPeripheralManager = CBPeripheralManager(delegate: self, queue: DispatchQueue.main, options: nil)
  34.              
  35. lazy var region: CLBeaconRegion = {
  36.          
  37. guard let uuid = UUID(uuidString: "xxx" ) else {
  38. return CLBeaconRegion()
  39. }
  40. let major: CLBeaconMajorValue = 1
  41. let minor: CLBeaconMajorValue = 1
  42. let id = "the name of the created Bluetooth base station"  
  43. let region = CLBeaconRegion(proximityUUID: uuid, major: major, minor: minor, identifier: id)
  44. return region
  45. }()
  46.      
  47. func peripheralManagerDidUpdateState(_ peripheral: CBPeripheralManager) {
  48.          
  49. switch peripheral.state {
  50. case CBManagerState.poweredOn:
  51.              
  52. if let data = self.region.peripheralData(withMeasuredPower: nil) as ? [String : Any ] {
  53.                  
  54. self.peripheralManager.startAdvertising(data)
  55. }
  56.              
  57. case CBManagerState.poweredOff,
  58. CBManagerState.resetting,
  59. CBManagerState.unauthorized,
  60. CBManagerState.unsupported,
  61. CBManagerState.unknown:
  62.              
  63. break
  64. }
  65. }
  66.     
  67. func peripheralManagerDidStartAdvertising(_ peripheral: CBPeripheralManager, error: Error?) {
  68.          
  69. }
  70.          
  71. }

4. (To be improved) I have tried the solution at the end of the article on iOS anti-black industry false location detection technology. I read the fLocation of CLLocation's _internal through kvc layer by layer, but I can only read this far. If I read it through kvc again, the following error will be reported:

  1. Expression can't be run, because there is   no JIT compiled function  

After further research, I found this explanation in Apple's official development documents [4]. It also said to set the debug+ optimization strategy, but the default bug environment of iOS is -Onone level. In fact, the main reason seems to be that the JIT setting can only be found in the Hardened Runtime of Signing & Capabilities when developing the Mac client. About the setting of Allow Execution of JIT-compiled Code (official article [5]). In the end, I can only get here. If there is a great god who can read the real location of CLLocation through other methods (this is an extremely perfect solution), please feel free to enlighten me.

Attachment:

The official definition of the CLLocation object private variable _internal instance object [6]:

  1. @interface CLLocationInternal : NSObject {
  2. struct {
  3. int suitability;
  4. struct {
  5. double latitude;
  6. double longitude;
  7. } coordinate;
  8. double horizontalAccuracy;
  9. double altitude;
  10. double verticalAccuracy;
  11. double speed;
  12. double speedAccuracy;
  13. double course;
  14. double courseAccuracy;
  15. double   timestamp ;
  16. int confidence;
  17. double lifespan;
  18. int type;
  19. struct {
  20. double latitude;
  21. double longitude;
  22. } rawCoordinate;
  23. double rawCourse;
  24. int floor;
  25. unsigned int integrity;
  26. int referenceFrame;
  27. int rawReferenceFrame;
  28. } fLocation;
  29. CLLocationMatchInfo * fMatchInfo;
  30. double fTrustedTimestamp;
  31. }
  1. @class NSData;
  2.  
  3. @interface CLLocationMatchInfo : NSObject <NSCopying, NSSecureCoding> {
  4.  
  5. id _internal;
  6. }
  7. @property (nonatomic,readonly) long long matchQuality;
  8. @property (nonatomic,readonly) CLLocationCoordinate2D matchCoordinate;
  9. @property (nonatomic,readonly) double matchCourse;
  10. @property (nonatomic,readonly) int matchFormOfWay;
  11. @property (nonatomic,readonly) int matchRoadClass;
  12. @property (getter=isMatchShifted,nonatomic,readonly) BOOL matchShifted;
  13. @property (nonatomic,copy,readonly) NSData * matchDataArray;

References

[1]

How to use code to determine whether the iOS system is jailbroken: https://www.huaweicloud.com/articles/7c6b8027253c4a97196d359840f638d9.html

[2]

iOS anti-black industry false location detection technology: https://cloud.tencent.com/developer/article/1800531

[3]

Wifi positioning principle and iOS Wifi list acquisition: http://www.caojiarun.com/2017/01/iOS_Wifilist/

[4]

Allow Execution of JIT-compiled Code Entitlement: https://developer.apple.com/documentation/bundleresources/entitlements/com_apple_security_cs_allow-jit

[5]

Hardened Runtime: https://developer.apple.com/documentation/security/hardened_runtime

[6]

Official definition of _internal instance object: https://github.com/nst/iOS-Runtime-Headers/blob/master/Frameworks/CoreLocation.framework/CLLocationInternal.h

<<:  WeChat launches "Send Now Pay Later" service: courier picks up and leaves without waiting

>>:  Android advanced Kotlin high-order function principle and Standard.kt source code detailed explanation

Recommend

10 Mistakes Every Entrepreneur Should Avoid

[[156534]] I like every entrepreneur, so I really...

Hortonworks Ted Yu: Tiny LFU, a highly efficient cache admission policy

[Original article from 51CTO.com] On November 25,...

How to design a landing page? From creativity to launch, the whole process!

A loading page is also called a landing page. It ...

36 lessons to help you become an Excel expert

Contents: /36 lessons to help you advance from a ...

Meituan Operations: 6 strategies for [Meituan Takeaway Membership]!

Today I want to share a project with you, which i...

How to promote Kuaishou? Share the promotion method of Kuaishou live broadcast!

How to promote Kuaishou live streaming ? In 4 yea...

How to plan a successful event marketing? You need these 3 traits!

Before officially launching event marketing , you...

The world's deepest underground laboratory has made important progress!

Wang Jing, Wang Chao, Shen Qiushi, Science and Te...

Behind the WeChat outage response: pretentious texts, powerless users

WeChat had a malfunction yesterday afternoon, and...

Baidu bidding creative writing, how to write a good creative idea?

A good creative can not only improve the ranking ...