Hacker News new | past | comments | ask | show | jobs | submit login
Compromising Garmin Sport Watches: A Deep Dive into GarminOS and Its MonkeyC VM (anvilsecure.com)
176 points by anishathalye on April 22, 2023 | hide | past | favorite | 74 comments



MonkeyC is such a funky language to write. It's obviously modeled on top of java, just with some syntactic differences making it instead look like a mashup with javascript.

I get why they made their own high level language to some extent, instead of shoehorning in something else. But making your whole stack from scratch must lead to lots of holes like these.

But a very nice blog post. Learned loads more about what's going on under the hood, very interesting.

Weird how permissions is mainly a UI thing. Aka how they're used is that if you have them you can use them, and it's mainly a UI thing to just show the same list in the app store. So not really enforced. I guess the fix then is to make sure it's not possible to lie in the app store?


Forget the language, it is their pun that bugs me. I guess it is Monkey See Monkey Do? But, my brain really wants MonkeyC to be the compiler for the Monkey language.


My sense, as someone who has written more than one CiQ app is that Garmin got caught completely by surprise with the popularity of 3rd party apps on wearable platforms and MonkeyC graduated from “interesting side project” to “critical ecosystem capability” in the space of a couple months, years ago. The early CiQ SDK versions had some truly insane conventions like using constants named “THAI_SPICY_HOT” for font sizes, and the development platform (as others have noted in this thread) has always been a barely functional tool chain with minimal error handling, no compiler optimization, no debugger, simulators that don’t match the device ROMs, etc etc.

For a long time this didn’t really matter since the Apple Watch and Garmin devices really appealed to two very different market segments - Garmin had a huge moat in first party fitness capabilities, maps, and battery life, and Apple had a huge moat in UX, their app ecosystem, the screen quality and device style, and smartwatch functionality.

Now, both companies are closing the gap in both directions on many of these aspects. It will be interesting to see what effect (if any) this will or will not have on the CiQ tooling and the CiQ ecosystem.


Your remark seems to match what I've observed during the reverse engineering part of the project. With magic constants like `0xc0debabe` [0] or opcodes like `canhazplz` [1] that you would expect more from a student CS project for instance.

[0]: https://github.com/anvilsecure/garmin-ciq-app-research/blob/... [1]: https://github.com/anvilsecure/garmin-ciq-app-research/blob/...


Yeah, exactly. THAI_SPICY_HOT was just one of many signals that I got that the MonkeyC project could have very much started out as an intern project or similar.

The list of languages the documentation claims MonkeyC takes inspiration from also denotes a certain type of programmer background:

> C, Java™, JavaScript, Python™, Lua, Ruby, and PHP all influenced the design for Monkey C

(source: https://developer.garmin.com/connect-iq/monkey-c/)

If I asked an embedded hardware expert to design a novel programming language for my highly resource-constrained wearables platform, I would be very surprised if these were the language touch points they used as their references in the design brief.


Anyone got a recommendation for fitness wearables where you can opt out of having to sign up with an account, and can export data out of it in open/standard formats?


Garmin watches work well with the desktop sports tracking program MyTourBook.

I've never had to activate a Garmin watch or register it online in order to use it. Not connecting it to Garmin Services and apps may limit access to 3rd party apps, or at least make it harder to load them load though. (I haven't researched side loading since base features are fine for me).

MyTourBook supports FIT/GPX/TCX/etc, has maps, calendars, charts and activity classification. It's built with Java so can run at least on Windows and Linux. There may be other good programs now, but as of a couple years ago it appeared to be among the better options.

It's open source (and they were supportive of PRs for improving Garmin import).

https://mytourbook.sourceforge.io/mytourbook/index.php

Edit: It's also not limited to Garmin devices. There is support for formats from Suunto, Polar and some other companies. https://mytourbook.sourceforge.io/mytourbook/index.php/docum...

Edit 2: This is with syncing over USB btw.


I use ActivityLog2 which also reads FIT files.

https://github.com/alex-hhh/ActivityLog2/releases


> This is with syncing over USB btw.

Nevermind it is not worth the trouble, vs handing in anonymized data with a temp email


Right, anonymized data that shares your vitals 24/7 (which are fairly unique) and location data which totally cannot infer your home and work locations. You’re deluded if you believe this can truly be anonymized and stay anonymized.


Depends on the device I'm guessing. AFAIK, not all Garmin devices log location 24/7, but only when explicit activities have been started.


Don't a lot of people start and/or end their regular fitness runs or bike rides at their doorstep? The thing about these fitness tracking tools is that you start wanting to track all your activities to get the statistical trends. It becomes integrated into your day to day lifestyle.


I currently live in a metropolitan area, so no, I don't. I usually have a brisk walk until I reach the place I consider the starting point, as where I live it's not very comfortable to run, and it's not until then I start tracking the exercise.

Most of my friends who exercise also does it at places at least a couple of hundred meters away from their home. The ones that live outside the city, probably do start their run right outside their doors though.


Yes, that is common practice for some athletes. The Garmin Connect platform has pretty good privacy controls which allow users to hide activities or mask tracks near certain locations. Of course if Garmin gets hacked then all of the raw data could be exposed, but the same concern applies to smartphone platforms as well.


I am always using Garmin devices locally as an USB drive. You can access all your workouts, planned structured workouts, routes, calender via the USB drive. This is why I am still with Garmin. I did not find any other manufacturer providing this. In fact I always upload my executed workout .fit files directly from the watch into Tredict. The planning and analysis software I am using.


I'm not aware of any major brands that offer account free service. The problem is that a smart device like this is not worth much without some kind of app ecosystem, app stores generally demand accounts, and browsing app stores from a watch is not exactly ideal.

As far as I know, Tizen smart watches can function well on their own after setting up the account once and I believe cloud synchronization is even optional. However, Tizen for smart watches is a dead end, with Samsung getting back to Android Wearable.

There's PineTime (https://www.pine64.org/pinetime/), which is very barebones but open source. Popular firmware, such as InfiniTime (https://github.com/InfiniTimeOrg/InfiniTime) can also be flashed onto several smart watches available on your favourite Chinese import stores (for example: https://github.com/StarGate01/p8b-infinitime for the Colmi P8).


PineTime looks like a fantastic product and if it supported GPS it would probably be the one that I purchase.

I've also seen this one mentioned in my research but would love to hear from anyone who's used it: https://banglejs.com/

Thanks for the InfiniTime links, I'll check that out.


I own a Bangle.js 2 and really wanted to like it. I have a pretty high tolerance for awkward workarounds to maintain a moral high ground, but it just was no fun. The touchscreen tended not to respond as expected - it seemed to regularly, but not always, have an input offset of around 20% of the screen. My first one's button broke despite minimal use due to the above - only really wore it as a novelty (it was replaced to be fair). The app ecosystem requires attention to stop different apps intefering with each other. The Gadgetbridge connection wasn't especially reliable for me. Etc.

I finally gave up when I found the tiny magnets which hold the charger on to the watch had fallen out and were lost when I went to charge it one day.


I own a BangleJS2. I don't use the fitness features but it works quite well on Android with GadgetBridge, a pricacy-focused smartwatch management app, and the OS and apps are all open-source. It was a bit rough around the edge when it came out, but so far it's been quite stable. I even made some PR fix some annoyances.

You can check all the available apps here, there should be something that will monitor which fitness activities you want, and the data can easily be exported from Gadgetbridge

https://banglejs.com/apps/


I am pretty sure you can use the sports tracking functions in garmin without an account, if not, at least without connecting the watch to a phone. You just need to connect with usb to copy the activity file (.fit) which can be converted to tsv.

regarding the passive tracking I dont have a clue


The main thing that I miss from connecting to Garmin Connect is downloading the EPO/CPE files which speedup acquiring the GPS data a lot. see https://support.garmin.com/en-US/?faq=6IbaJEHc1i9gydzQomXzyA

To avoid waiting up to several minutes to get the GPS data when I start my workout, I'll switch to an exercise mode to start acquiring the GPS data while I change into my workout gear and leave the watch near a window.

By the time I've finished changing, the GPS data is available and the watch will behave almost like I had downloaded the EPO/CPE files from Garmin Connect.



Really? I recently got a forerunner 265 and it definitely didn’t give the impression that was possible.

The battery life is also nowhere near the advertised length (13 days). Most disappointing is that their support people say to expect about 60% of that, which is what I’m getting.

That said, this will likely be the replacement for my Pebble. Battery life over 6 days, buttons to control music playback, and an English-first UI (amazfit falls down here).


I have an older model but I definitely can download the fit files over usb and using the garmin provided information/sdk to write programs to read the files. or just convert to tsv/csv using their provided utilities. if you can't use usb, you may be able to use bluetooth.


My 2S uses up 10–11% per 24h in watch mode (using the gps uses more battery). But I had to disable the O2 measurement altogether because that chewed through the battery and isn’t that useful to me.


Are you doing something special with the watch? I've gotten several weeks out of all my Garmin models except the first one I bought around 2005. Battery life is one of their main selling points and the only reason I have one over a proper smartwatch. Maybe have a second look at optimising the settings for battery life. There are quite a few recommendations on how to do that.


That model plays music and uses an OLED display. Playing music off the watch burns through battery IME and I'm betting how you've configured the OLED display matters. It's "Up to 13 days" and I'm guessing those 13 days don't involve using GPS, don't involve playing music and don't involve using always on display. Misleading maybe.


Yeah, and I don't do any of these things. I just get notifications from my watch and use it as a remote control for podcast playback/ffwd (from my phone to my AirPods). And I have AOD turned off.

The "up to 13 days" number is based on a specific set of behaviors/usage, [1] and the Garmin support people have not been able to explain why I'm not getting it. They have looked at logs for my device and have been content to say that 60% of the "up to" number is normal for their devices.

I was hoping for much better, especially considering the Verge's reviewer [2] said she was getting 6.5 days with AOD turned on, and was on track for 15 with it turned off. I wonder if she was given a bespoke unit by Garmin, which is better than the ones that we get in retail stores.

1: https://support.garmin.com/en-US/?faq=daNp4hnaAZ9Fg1XdFcZez5

2: https://www.theverge.com/23632332/garmin-forerunner-265s-rev...


Your 265 can be mounted as a usb drive, as can pretty any Garmin device for maybe 10+ years.


On a Mac, it requires some utility made for reading Android devices. It doesn't pop up as a drive when plugged in.

Can the device receive notifications from my iPhone without an account? That's one of the main reasons I use the device.


Yeah, because Apple doesn't support MTP at all. On OSs that do they just pop up.

I think to get notifications it has to use the app.


The SpO2 sensor uses significant battery life. This is why is princely only enabled during workouts and sleep, but it can be set to run nonstop or not at all. Double check that setting.

My 945 is pretty close to advertised when I’m not too active.


Yeah I have this disabled. I’ve chatted with their support team several times and they’ve confirmed my settings are about as low-energy as possible (aside from disconnecting from my phone, which would defeat the purpose).


Checkout GadgetBridge and their list of supported devices. It runs completely offline. There is differing level of support so make sure to read the details. The mi bands are cheap option that works pretty well. I've got a Skagen (really a fossil) hybrid that works with GadgetBridge, but doesn't support sleep tracking unless you use Skagen's app. But I disabled network access for their app and it works perfectly fine. Would be nice if someone wrote a sleep analysis plugin for GadgetBridge for devices like this that don't do the analysis on the hardware. Pretty happy with the device nonetheless.


Garmin I’m fairly certain you can do everything ‘locally’ over usb and a laptop. I think Connect requires an account though


We had one. It was called Pebble. And then they kickstarted a watch for 3 million and decided to sell themselves to fitbit instead.


They never shipped out my Pebble Time 2 before the project (and company, for that matter) got shelved. Something I'm still sad about even today.

No other smartwatch released before or since has even come close to Pebble's Pebbles.

Kickstarter page is still up: https://www.kickstarter.com/projects/getpebble/pebble-2-time...


Look at the supported wearables for GadgetBridge

https://codeberg.org/Freeyourgadget/Gadgetbridge

FOSS, doesn't have network permissions, can export data or interface with other apps


+1 for this. It makes my Amazfit watch from a privacy nightmare into a great cheap privacy conscious watch.

I just wish it could export SpO2 values and update the AGPS almanac. Because of this a GPS lock takes very long.


Late Amazfit watches require online signup in a quite cumbersome way in order to pair.


I can also vouch for Gadgetbridge being a great option.

I use it with a MiBand 6.


Only tangentially related, but let me plug my new project https://cubetrek.com, a Strava alternative for viewing and managing your GPS tracks.

As discussed in https://news.ycombinator.com/item?id=35671245


you can download the files from the garmin using usb and the format of the activity files is documented publicly. There's an SDK and some utilities to convert to csv/tsv too.


I used to buy Garmin fitness bands, but they seem to have been discontinued. Among other things, I wore them overnight and use them as an alarm clock. Having a charge that lasts 7+ days is such a huge benefit imho. Does anyone have any other recommendations? I currently have a Fitbit, but I would also prefer a model that didn’t have an associated cloud account.


Most current Garmin watches have 7+ days of battery life depending on how much you use the GPS.


I would prefer wearing a lightweight band overnight. I wish Garmin still made the Vivo* models


I wear a Forerunner 735xt, time for anecdata!

It may be bigger than a band but it's surprisingly small and very light to the feel, I barely notice the difference with the Fitbit Charge HR 2 I owned before. Major reason why I'm not upgrading to a Fenix of something like that.

Plus up to 15 days on battery when not using GPS, much more if I disable continuous HR.


Personal preference but I find the Venu so light that it does not bother me for sleep the way my Fossil Explorist did (which also never had enough battery to do overnight tracking!)


You may check also goldencheetah https://www.goldencheetah.org/. It is open source app for offline use.Have tons of features.


I haven't tried one as I am currently happy with my Garmin vívoactive 3, but the BangleJS 2 looks very interesting: https://banglejs.com/


I know my COROS Pace allows for data export, but you probably need an account.


Yeah I have the same watch. The app isn't in the Google Play store, you have to download it straight from the company. Given that its half Chinese company it really isn't going to be better than Garmin.


You need an account for that. As a bonus you download your files from the Alibaba Cloud fronted by Cloudfare. Garmin gives you local usb drive access to their devices.


I've long wished for a Cyanogenmod (LineageOS) for Garmin

But without source that can't ever happen I guess.

Also I think they encrypt firmware after the 5 series in the Fenix 6/7 models

Coros has proved it is possible to use cheap hardware to make clones but their metrics are supposedly nowhere near as good as the Firstbeat algorithms.


Author here.

They did start encrypting the firmware of their latest devices. I noted that the firmware images for Forerunner 55, 945 and 955 were encrypted. Most likely others are as well.

In the live demo I did at Hack in the Box a couple of days ago (slides available [0]) I've shown how to exploit one of the vulnerabilities to read the memory of the Forerunner 55, making it possible to dump the firmware unencrypted. The CIQ demo app is also on our GitHub repo [1].

[0]: https://conference.hitb.org/hitbsecconf2023ams/materials/D2T... [1]: https://github.com/anvilsecure/garmin-ciq-app-research/tree/...


I’m very impressed by the level of technical detail in this post.

I’m somewhat surprised garmin made their own language for apps but considering the low power processors they target was their any other options?


Pebble ran third party native apps (generally written in C) sandboxed via the ARM SVC/USR-mode privilege system, integrated with the onboard MPU.

Fitbit - after hiring many Pebble staff - supports third party apps written in JavaScript. These run on the pre-existing JerryScript engine, and are still sandboxed on the native side should the VM have holes. This made it much easier to get started as a developer, but imposed an upper limit on app performance vs. the native apps seen on Pebble.


Author here. Thanks!

I am surprised as well, especially considering that their compiler does little to actually no optimization. For instance, it won't remove dead code or unused variables. These seem like low hanging fruits that could save memory and cycles on low power devices.


strict subset of JVM, like the old days of mobile phones and SIM cards


Great article. I've owned a bunch of Garmin devices. Right now I'm not sure if any of them even support Connect IQ. When I tried Connect IQ the apps rarely did anything I much cared about.

If I cared about that kind of thing I'd be wearing an Apple Watch. I like the Garmin devices cause they're so much simpler and does the specific built in sports functionality very very well. They are also far more tailored towards being functional whether or not you have internet connectivity.

I would far far prefer Garmin to make Garmin Connect on iOS/Android work without internet connectivity than almost anything else. It's ridiculous the devices (this is not just watches) can't sync to the phone for you to review data on the phone if you there is no internet. What they do right now is send everything from the device right to the cloud, then have the phone download something else from the cloud.

In my case one of my devices (Edge 1030) is completely capable of mapping and navigation without any internet connectivity but you can't do anything on the phone with the data till you return to internet connectivity.

Garmin even has another app (Explore) that has mapping on the phone without internet connectivity once you download the maps. The mapping data in that app is amazing. Yet Garmin Connect only works with Apple Maps data, not Garmin's own map data. When you're on the Garmin device you get a vastly superior map compared to what Apple maps can provide!


> I like the Garmin devices cause they're so much simpler and does the specific built in sports functionality very very well. They are also far more tailored towards being functional whether or not you have internet connectivity.

I wholeheartedly concur with your point. Garmin watches excel at sports tracking as their primary focus, with notifications and messaging features taking a backseat. Conversely, Apple and Google watches prioritize communication functions.

Previously, I owned an Android Wear watch, primarily for monitoring my runs. Although it sufficed, I found myself wearing it exclusively during runs. The device required daily charging, had an irritating touchscreen, and lacked navigation capabilities without being paired to a phone, despite its built-in LTE modem.

A few months ago, I opted to purchase a Garmin Fenix 6 watch. Upon using it for several days, I recognized that this was the device I had initially sought. The battery life spans two weeks—although heavy GPS use reduces this to about one week—and the watch includes maps for the entire United States. I have found it invaluable for hiking, running, and more, and its exceptional performance has led me to wear it continuously rather than solely during activity tracking.


> The Atredis' CVE-2020-27486 advisory explains that the news opcode allocates the string buffer based on the length specified in the string definition, and then proceeds to call strcpy to copy the string bytes. This can lead to memory corruption, since strcpy does not use the specified length and will only stop at the first null byte.

How can seemingly talented developers KEEP MAKING THIS MISTAKE? It is like almost every police officer shooting themselves in the foot with their service gun.


When smart people keep making the same mistakes, we need to realize that there's a problem on the systemic level.

In this case: C is riddled with these easy-to-make mistakes, and it's not enough to think that "a smart developer" is able to avoid these mistakes, but that everyone will make these (or similar) mistakes as long as we're allowed to.

It's one reason why I'm so big on Rust: because these mistakes are much harder to make.


No “user/kernel mode”, yikes, esp when executing third party apps. I guess since all the third party code is executing in a VM, this could be much safer with verification up front and no dynamic code execution.


Pretty cool what they did. There doesn't seem to be a mainstream embedded OS that allows dynamically loading binaries, but it would be so nice.


If by "embedded" you mean "MMU-less", it's definitely rare these days, even though historically general purpose computers had binary loaders long before they had virtual memory.

NuttX is the only one I can think of off the top of my head with this feature.


> There doesn't seem to be a mainstream embedded OS that allows dynamically loading binaries

I'm not up to date on embedded programming vernacular, but isn't that just a regular OS with apps? (Apple Watch OS, Android Wear, etc)


What is the "so what" here? Are these internet connected?


During workouts internet connection is only through bluetooth to the companion app and by this somewhat regulated, but for updates, offline music storage and the like most also have wifi.

Tangent: that bluetooth uplink comes with some bewildering differences for those monkeyC apps, e.g. a request started to be consumed as json will happily talk to localhost on the companion app's host. A request started to consume a navigation itinerary will also do, except when the host isn't on the internet, then it fails to read localhost.


Author here. Fair question!

They get access to the internet via the Garmin Connect companion app. But if you're asking to know if they can be exploited from the internet, that's not what we showed yeah.

The vulnerabilities we've disclosed require a malicious app to be installed (e.g. from the CIQ app store) so let's not cry wolf.

What I think this project highlights and what we should remember is the current level of security of Garmin devices.

GarminOS deploys none of the security mitigations one would expect in modern devices (let's exclude crappy IoT devices flooding the market). No stack canaries, no W^X, etc. It does not implement isolation between user-supplied code and the rest of the OS either. And their C code base does not appear to receive much scrutiny in terms of security review.

It would be much easier to exploit the watch (e.g. sending a malicious message to the user's phone that sends it to the watch to show the notification) than exploit the user's smartphone. And this could be performed from the internet.


Indeed there have been software defects that caused Garmin watches to crash when displaying certain text messages.

https://forums.garmin.com/outdoor-recreation/outdoor-recreat...


Do you have thoughts on the NFC and particularly Garmin Pay features?

I wonder if these are secured differently or merely obscured behind the encrypted firmware on newer models.


It's not something I've encountered yet so I don't have any insight to share. I would be surprised if they were secured differently but I'm purely speculating here.


There is an appstore with third party apps.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: