Apple Health Accuracy & Reliability
Ian Whiffin
Posted: 28th June 2025
Revised: 2025-06-29

Despite working on Apple Health for years, and writing a couple of blogs about it already, I have never really written about the accuracy of it - others have written about it already and my opinion doesn’t differ much from the details already published.

Despite that, I think there are a couple of nuggets of information here that could be useful to know. So let’s dig in...

The Details

The Files
The two files we’ll be looking at are:

  • /private/var/mobile/Library/Health/healthdb_secure.sqlit
  • /private/var/root/Library/Caches/location/cache_encryptedC.db

Apple Heath testing was focused on both the data found in healthdb_secure.sqlite and cache_encryptedC.db to determine the possibility of erroneous flight climb events or steps/distance being recorded while the device was travelling in a vehicle.
Further to that, the accuracy of the number of steps and distance travelled was tested for accuracy

.
Cache_encryptedC.db
Cache_encryptedC.db’s StepCountHistory table contains several fields that appear related to timestamps.

startTime

This field consistently has a timestamp value that appears relevant to physical activity occurring.

timestamp

This field is always increasing like a timestamp but cannot be converted to a typical timestamp value.

activeTime

This field is always increasing like a timestamp but cannot be converted to a typical timestamp value.

firstStepTime

This field does not always contain a value, although when it does it is around 3 seconds earlier than the startTime.


The rest of the fields in the table track the total number of steps taken, meters travelled, floors ascended or descended etc.

When referring to records in this database, the startTime field was chosen as the most appropriate field to use as a timestamp and the activity was inferred from the difference in field values.

For example, if records existed which showed:

startTime

floorsAscended

12:00:02

100

12:00:08

101


This would indicate that that 12:00:08, the device detected a single floor was ascended as the value differs by one from the record which precedes it.

Likewise, if records existed which showed:

startTime

count

12:00:10

1000

12:00:20

1005


This would indicate that that between 12:00:10 and 12:00:20, the device detected 5 steps were taken as the value differs by 5 between the two records.

 

Flights Climbed Times - Healthdb_secure.sqlite vs cache_encryptedC.sqlite

Test Scenario
This test sought to find out the accuracy of the timestamps recorded in both the Health database and cache_encryptedC databases.

The test involved placing 8 iPhones (various models/iOS versions) on a tray and ascending 2 flights of stairs twice. The total altitude difference between the top and bottom was slightly over 6m. At the half way point was an approximately 3m long landing.

The first ascent took place between 11:53:00 and 11:53:15 with a 45 second pause on the landing before the second flight was started. The second flight occurred between 11:54:00 and 11:54:16.

The second ascent started at 11:55:30 and occurred over the next 25 seconds with no prolonged pause on the landing.

Given Apple’s definition of a “Flight” being approximately 3m altitude gain over 16 steps, it was reasonable to postulate that 4 Flights should be recorded on the devices.

Test Results - HealthDB_secure.db [Samples]

Device

iOS Version

Start Time

End Time

Flights Climbed

iPhone 8

14.2

11:53:27

11:56:00

3

iPhone X

15.2.1

11:53:28

11:56:09

4

iPhone 6s

15.8.3

11:53:28

11:56:13

4

iPhone X

16.7.5

11:53:27

11:56:09

4

iPhone X

16.7.10

11:53:28

11:56:10

4

iPhone SE (2)

17.5.1

11:53:19

11:56:10

4

iPhone Xs

17.6.1

11:53:21

11:56:10

3

iPhone 12

18.1

11:53:26

11:56:11

4

 

As can be seen from the table above, most devices recorded 4 flights climbed as expected. 2 devices only recorded 3 flights.
In general, the recorded Start Time was between 20 and 30 seconds after the actual start time of the ascent and the End Time was 10 to 15 seconds after the ascents were completed.


Test Results - cache_encryptedc.db [StepCountHistory]

Device

iOS Version

First Flight

Second Flight

Third Flight

Fourth Flight

iPhone 8

14.2

11:53:30

11:54:46

11:56:00

-

iPhone X

15.2.1

11:54:07

11:54:50

11:55:59

11:56:09

iPhone 6s

15.8.3

11:54:06

11:54:47

11:56:00

11:56:13

iPhone X

16.7.5

11:53:30

11:54:49

11:56:00

11:56:10

iPhone X

16.7.10

11:54:06

11:54:51

11:56:00

11:56:10

iPhone SE (2)

17.5.1

11:54:05

11:54:46

11:59:59

11:56:10

iPhone Xs

17.6.1

11:53:29

-

11:56:00

11:56:10

iPhone 12

18.1

11:54:07

<11:55:37

11:56:00

11:56:11


*Note that due to a delay in extraction of the iPhone 12, some cache_encryptedC.db records had been purged and were unrecoverable. This included the exact time of the Second Flight ascent. All that could be ascertained is that it occurred prior to 11:55:37.

The cache_encryptedC.db data allowed a more granular view at the data and actually see when each flight was recorded as completed (I say completed as these times are derived from when the device recorded an increase in the flightsClimbed field - so although it didn’t tell me when the climb started, I know when the altitude difference was recognized).

This data has been laid out on the graph below.

  • The solid green bars that run vertically across the graph are the actual times of the ascents.
  • The solid red lines which run horizontally indicate the timespan reported by HealthDB and the number of flights climbed during that time is shown at the far right.
  • The red crosses show the time that the ascent is recognized and written the cache_encryptedC.db.
  • The dotted red line shows that there is no definitive time for this record due to record purging.

As can be seen on the graph, in all cases where a flight ascent was recorded, on average, the timestamp shows between 15 and 50 seconds after the ascent was completed.

In the case of the two consecutive flights being ascended, the first flight was recorded in cache_encryptedC.db about 15 seconds after the midway point of the ascent, and the second flight had a timestamp 15 seconds after the ascent was completed.

Conclusion
The conclusion drawn from these tests is that the timestamps shown are not necessarily exactly when the activity took place. It may be obvious to state, but the iOS device is reactionary to the altitude increase, which needs to be detected by the device for the record to be created. This is definitively observed to occur once the flight climb is completed.

The time period provided from Apple Health provides a good general idea of when the flight climb activity happened and the cache_encryptedC.db data, if present, can provide an additional level of fidelity even though the timestamp is in general ~15 to ~35 seconds post ascent.

 

Steps & Distance

This test was designed to evaluate the accuracy of the Steps and Distance taken during the recorded Health events.


Test Scenario
A Rugby field with a known distance between the goalposts was visited. According to pitch specifications, the distance between the goal lines should be between 94 and 100m.

The distance was measured using Google Maps “Measure Distance” feature and found to be 91.5m.
The distance was also calculated using the GPS coordinates at each goal post and found to be 91.41m.

3 iPhone X devices were used for the testing and were all in an “off” state until the testing started.

One device was placed in a right trouser pocket, one device in a left trouser pocket and one device was held as though being viewed.

At 15:46:00, the test began, and the devices were walked from one goal line to the other, arriving at 15:47:18 and taking 118 steps. At this point, 3 additional steps were taken in order to turn 180 degrees ready for the return journey.

At 15:54:00, the walk back to the start began, ending at 15:56:25 and taking 119 steps.

The devices were then turned off again.

In total, 237 steps were taken while walking + 3 steps to turn around, and a total of 183m was covered.

Upon extraction of the devices, their data from both HealthDB_Secure and cache_encryptedC.db was checked.

Device 1: iPhone X with iOS15.2.1

This device had been placed inside the right trouser pocket.
HealthDB_Secure.db recorded 2 samples:

Start Time

End Time

Steps

Distance (m)

15:46:04

15:48:39

218

119.6

15:56:05

15:56:21

21

13.9

Combined, these records show a total of 239 steps covering 133.5m.

The total number of steps was as near as could be expected however the distance covered was around 50m short of actual distance.
Cache_encryptedC.db recorded 53 records which could be broken into two distinct groups;

  1. 15:46:07 through to 15:48:39 - 19 records showing 119 steps.
  2. 15:55:03 through to 15:56:23 - 32 records showing 120 steps.

This is a total of 239 steps, matching what the health database provides.

 

Device 2: iPhone X with iOS16.7.10

This device had been placed inside the left trouser pocket.
HealthDB_Secure.db recorded 2 samples:

Start Time

End Time

Steps

Distance (m)

15:46:05

15:56:03

210

123.4

15:56:03

15:56:23

25

14.9

Combined, these records show a total of 235 steps covering 138.3m.

The total number of steps was very close to the actual number of steps however the distance covered was still around 50m short of actual distance.
Cache_encryptedC.db recorded 64 records which could be broken into two distinct groups;

  1. 15:46:05 through to 15:47:29 - 33 records showing 118 steps.
  2. 15:55:04 through to 15:56:23 - 32 records showing 117 steps.

This is a total of 235 steps, matching what the health database provides.

 

Device 3: iPhone X with iOS16.7.5

This device was held.
HealthDB_Secure.db recorded 5 sample times:

Start Time

End Time

Steps

Distance (m)

15:46:03

15:56:03

218

158.4

15:56:03

15:56:08

8

18.2

15:56:08

15:56:13

7

-

15:56:13

15:56:19

8

-

15:56:19

15:56:21

3

-

Combined, these records show a total of 244 steps covering 176.6m.
The total number of steps was slightly above the actual number of steps however the distance covered was the closest of all devices tested.
Cache_encryptedC.db recorded 64 records which could be broken into two distinct groups;

  1. 15:46:03 through to 15:47:33 - 34 records showing 123 steps.
  2. 15:55:04 through to 15:56:23 - 32 records showing 121 steps.

This is a total of 244 steps, matching what the health database provides.

All of the results from the cache_encryptedC.db database were plotted onto the below graph. The shaded areas indicate when the walking activity was actually occurring.

 

Distance walked in meters as reported by Health

 

Conclusion
Both the Health database and cache_encryptedC.db gave a step count which was remarkably close to the actual number of steps taken.

Cache_encryptedc.db also provided a highly granular view of the data the majority of the time.

Overall, the number of steps taken and the time period in which they were taken are reasonably accurate.

The recorded distance travelled by each of the devices was typically under-reported.

Throwing / Shaking Device

This test involved shaking and throwing phones while staying stationary to see if step or flight climb activity would be recorded when there was no lateral movement.


Test Scenario
Multiple devices were shaken, swung and thrown around in various ways and speeds to see if any health data was ever recorded.


Conclusion
Cache_encryptedC.db was found to have recorded a small increase in steps during the time of the shaking/swinging/throwing activity. These records were ultimately aggregated into the main Health database as Steps Walked. No Flights Climb events were ever recorded.

 

Vehicular Travel (Test 1)

Test Scenario:
2 devices were taken on a journey which lasted between 16:30 and 19:30 and included several stops.

At all times that the devices were in motion, Apples Maps was on screen to ensure a constant stream of location data being recorded.

Because Apple Health records the data in segments, the devices were placed into the car over an hour before the journey started and removed over an hour after the journey ended to avoid any contamination of the data.

Leg 1: 16:30 - 1645
During leg 1 of the journey, the devices were left static in a dock. The only movement they were subjected to, was the natural movement and vibration of the vehicle when in motion.
Leg 1 included roads which were both up and down hill, and roads with various speed limits ranging between 30kph and 80kph.
Device 1: No Steps/Distance or Flight Climb events were recorded.
Device 2: No Steps/Distance or Flight Climb events were recorded.

Leg 2: 17:25 - 17:56
During leg 2 of the journey, the devices remained static in the dock.
Leg 2 was mostly flat road with only a small variance in altitude and mostly roads of 50kph.
Device 1: No Steps/Distance or Flight Climb events were recorded.
Device 2: No Steps/Distance or Flight Climb events were recorded.

Leg 3: 19:05 - 19:30
During leg 3, both devices were held by a passenger in the vehicle. They were not being interacted with but were now subject to additional movement caused by the holders’ arm reacting to the vehicle’s movements.
Leg 3 included roads which were up and down hill and were typically around 50kph.
Device 1: Recorded 329 Steps/258m and 13 Flights climbed.
Device 2: Recorded 352 Steps/274m and 14 Flights climbed.

Conclusion
This test demonstrated that a device being held by a person while travelling in a vehicle is capable of recording Steps, Distance and Flight Climb events, whereas a device being held in a dock appears to not suffer from the same issue.

 

Vehicular Travel (Test 2)

Test Scenario:
3 Phone X devices were driven on the same hill as the previous test 3 times.
The hill increased from an altitude of 1118m to 1158m according to https://en-ca.topographic-map.com.
The altitude of the devices was monitored at the bottom and top of the hill using the altimeter information available in the Compass application.
The altimeter reading of all devices at the bottom of the hill registered 1120m and the altimeter of all devices at the top of the hill registered either 1160m or 1170m, an increase of 40m - 50m.

40m equals approximately 13.3 flights according to Apple's flight climb definition (3 meters per flight).


The Map and Altitude information as per https://en-ca.topographic-map.com

 

Phone 1 - iPhone X with iOS 16.7.5
Phone 2 - iPhone X with iOS 15.2.1
Phoner 3 - iPhone X with iOS 16.7.10

  • The first time, Phone 1 was held in the same loose manner as described in test 1 while Phone 2 and Phone 3 were rested on a seat.
  • The second journey up this hill, Phone 2 was held while Phone 1 and Phone 3 were rested on a seat.
  • The final journey saw Phone 3 being held while Phone 1 and Phone 2 were rested on a seat.

Speed was kept at an average of 45 to 50 kph (28 – 31mph) and all 3 phones had a data connection and were focusing on Apple Maps to ensure constant location data.

 

Phone 1 – iPhone X with iOS 16.7.5
Phone 1’s test journey occurred between 11:41:55 and 11:44:00.
A Health Event was recorded in healthdb_secure.sqlite between 18:41:53 and 18:43:02 consisting of 54 Steps over 41m distance but zero flight climb events were recorded during this time or throughout the entire 3 journey test in either Healthdb_secure or cache_encryptedc.db.

Phone 2 – iPhone X with iOS 15.2.1
Phone 2’s test journey occurred between 11:46:22 and 11:48:26.
Two Health Events were recorded in healthdb_secure. The first event was between 11:46:33 and 11:48:22 consisting of 180 steps over 147m. The second event was a Flight Climb event which occurred between 11:47:08 and 11:48:30 and consisted of 13 flight climb events
No additional flights were recorded outside of this journey.

Timestamp

Count Change

Total Flights

11:47:11

24 > 28

4

11:47:26

28 > 29

5

11:47:36

29 > 30

6

11:47:41

30 > 31

7

11:47:47

31 > 32

8

11:47:57

32 > 33

9

11:47:59

33 > 34

10

11:48:10

34 > 35

11

11:48:17

35 > 36

12

11:48:30

36 > 37

13

 

Phone 3 – iPhone X with iOS 16.7.10
Phone 3’s test journey occurred between 11:50:55 and 11:52:56.
Two Health Events were recorded in healthdb_secure. The first event was between 11:50:57 and 12:00:49 consisting of 256 steps over 208m. The second event was a Flight Climb event which occurred between 11:51:09 and 11:52:56 and consisted of 13 flight climb events
No additional flights were recorded outside of this journey.

Timestamp

Count Change

Total Flights

11:51:12

68 > 69

1

11:51:27

69 > 70

2

11:51:35

70 > 71

3

11:51:42

71 > 72

4

11:51:58

72 > 73

5

11:52:11

73 > 74

6

11:52:13

74 > 75

7

11:52:15

75 > 76

8

11:52:21

76 > 77

9

11:52:28

77 > 78

10

11:52:43

78 > 79

11

11:52:49

79 > 80

12

11:52:56

80 > 81

13

 

This graph shows the Flight Climb event information from each device.
The blue area relates to Phone 1. The light area shows the time that the device was being held, and the darker area shows the time of the Health records which were recorded.
The orange area relates to Phone 2. The light area shows the time that the device was being held, and the darker area shows the time of the Health records which were recorded. The orange dots show the time of the recorded ascent.
The green area relates to Phone 3. The light area shows the time that the device was being held, and the darker area shows the time of the Health records which were recorded. The green dots show the time of the recorded ascent.

Wrapping Up

The testing above demonstrates several important things;

  • Cache_EncryptedC.db may be able to give more granularity than HealthDB_secure.db.
  • The number of steps recorded is a reasonably reliable indicator of steps taken when walking.
  • The distance is not as reliable.
  • It is possible to record both steps and flights climbed while in a vehicle if the device is held.

Overall, the Health app is a great source of forensic data, but as with most sources, there are nuances that need to be understood.

Previous Article
"CurrentPowerLog & the Monotonic Clock"
Next Article
"iPhone Internal Battery Temperature"
Search
Social