I bought my Flipper Zero on Xmas morning 2022 and began to play around with the various badges and old hotel room keycards I had, it really got me interested in digging deeper into understanding how data was stored on these devices.
RFID cards were pretty easy to figure out (we'll cover these in another article), but the hotel room keys took quite a lot more digging and experimentation to grasp. The first thing I did was search for the specification document which I found here.
While this article is designed to teach you how Access Bits work, I've also written a few Python scripts on my Github which automate the process among other tools and some hotel keycards in.nfc format scanned with my Flipper Zero.
The Mifare Classic (tm) 1K EV1 NFC is segregated into 16 sectors numbered 0 - 15. Sector zero is unique in that it contains manufacturer information and we'll touch on this at the end of the article. Each sector is broken down into four blocks of 16 bytes with block three being the Sector Trailer which contains KeyA (6 bytes), Access Bits (3 bytes), a user defined byte and KeyB (6 bytes). The remaining blocks (0-3) are for data. See figure A for a graphical representation.
In Figure A, you can see that Sector 15 has three blocks with block 3 being the Sector Trailer. We'll be focusing on the Sector Trailer for the remainder of this article and how it controls access to the three data blocks within that sector. It's important to note that each sector can have a unique Sector Trailer with different KeyA, KeyB and Access Bits.
In order to decode what access to data in a sector is allowed and by what key, we need to understand how Access Bits work.
As noted in Figure A, Bytes 6, 7 and 8 in block 3 (Sector Trailer) of each sector are the Access Bits. In Figure B, the left column shows bytes 6 - 8 respectively. At this point, I'd like to point out that byte 9 of the Sector Trailer is a user defined byte that can be used for whatever data you'd like to store there. You'll notice in Figure B that along the top row in grey is the binary representation of the hexadecimal byte with the Least Significant Digit (LSD) being on the right. You'll also notice that in blue are the bits we will be using to calculate our Access Bits and in purple are the negated bits used to checksum the Access Bits. If the negated bits aren't a correct inversion of the access bits, then it's considered corrupted and no access will be allowed to that block. This is a great way to screw up and accidentally lock a block or even a whole sector on your card.
Now, what is all the C1, C2 etc. stuff all about. Hold on, because this is where it gets weird. By the time we're done, we will have a set of four access rights comprised of three bits each, one for each block in that sector. They are C0 for block 0, C1 for block 1, C2 for block 2, and C3 for block 3 (Sector Trailer).
Figure C breaks down Figure B into color coded representations of where we pull our bits to make up our four block access rights. Let's start with the chart on the right. In order to build the Access Bits for block 0, we need the bits in yellow. For block 1, the bits in red. For block 2, the bits in green, and for block 3, the bits in blue. This is probably a good time to point out the subscript annotations. Notice they're 0 - 4 which maps to our four access rights for each block.
Sticking with the chart on the right, for C0, we need the bits C1, C2, C3 for subscript 0. For C1, we need C1, C2, C3 for subscript 1 etc. The right chart shows you which row and which column to retrieve those bits from. Let's throw some bytes into a color coded chart to work with. For reference Access Bytes FF 07 80 are the default Access Bits for a brand new card. This configuration is also referred to as 'Transport Configuration''.
In Figure D we've placed FF in byte 6, 07 in byte 7, and 80 in byte 8.
Alright, now let's get back to decoding Access Bits. To get C0, we need bits (row-column) 7-4, 8-0 and 8-4. Which looking at the chart on the right are 000. To get C1, we need bits 7-5, 8-1 and 8-5 and again on the right is 000. C2 we need bits 7-6, 8-2 and 8-6 which is 000 and finally, C3 where we need bits 7-7, 8-3 and 8-7 which is 001. So our Access Bits are as follows:
Block 0 - 000
Block 1 - 000
Block 2 - 000
Block 3 - 001 (Sector Trailer)
Great, now what? Well, now we need the secret decoder ring, but first let's take a quick moment to discuss the inverted checksum bits. If you
look at Figure C, you'll notice C1 is on the row for byte 7 as the first
four bits. In figure D, those bits are 0000. Referring back to Figure
C, you'll notice the inverted checksum bits are in byte 6 as the last
four bits. In Figure D, those are 1111. C2 is byte 8 last four bits 0000
with inverted checksum in byte 6 first four bits 1111. And finally, C3
is byte 8 first four bits 1000 with inverted checksum in byte 7 last
four bits 0111. Pretty wild huh? See figure E below for a graphical representation of that.
Now, about that secret decoder ring. There's actually two. One is for the Sector Trailer and the other one is for the data blocks. Let's start with the Sector Trailer Access Rights.
In Figure F, on the left side is our bits contained in C3 from above example which were 001. To keep the graphic smaller I condensed the text. In some access rights configurations, KeyA or KeyB can be used and is annotated in Figure F as A|B. Below is what each column represents.
R/KeyA - Can you read KeyA
W/KeyA - Can you write KeyA
R/DB - Can you read block 3, byte 9
W/DB - Can you write block 3, byte 9
R/KeyB - Can you read KeyB
W/KeyB - Can you write KeyB
Remarks - Something you should know about this configuration of Access Rights.
So let's get decoding. C3 was 001 which according to Figure F gives us the following permissions.
R/KeyA - No
W/KeyA - Using KeyA
R/DB - Using KeyA
W/DB - Using Key A
R/KeyB - Using KeyA
W/KeyB - Using KeyA
Remarks - KeyA can read KeyB
This Access Rights configuration is commonly called the Transport Mode because KeyA can do anything except read itself.
So, what's with the Remark? Well, it depends upon the security of the card data you are after. The reader must provide one of the keys, either A or B to the RFID chip in the card. To the best of my understanding, it only provides one key, not both. Therefore, if you're using both keys to control access to various blocks of data, you need to be able to read the other key using the key the reader gave you. This is why you oftentimes need to scan the reader with your Flipper Zero in order to derive the key it's giving you so can then read the other key if it's used to control access. I've seen many cards that only rely on KeyA to control access to data blocks with KeyB never being used at all.
Ok, let's move on to Data Block Access Rights.
If you remember, C0, C1 and C2 are the access rights to blocks 0, 1 and 2 respectively and they were all set to 000.
Let's break down the columns in Figure G.
Read - Can you read this block
Write - Can you write this block
Inc - Can you increment this block
DTR - Can you Decrement, Transfer or Restore this block
App - The typical application for these permissions
This configuration is referred to as the Transport Configuration and KeyA or KeyB can do anything, In Transport Configuration KeyA and KeyB are both set to FF FF FF FF FF FF.
One more thing to point out before we move on. Data Block Access Rights 110 and 001 identify a block as a Value Block which you'd increment or decrement to hold credits or monetary values. You may have also noticed 001 doesn't allow for incrementing, only read and decrementing, so this signifies a non-rechargable card.
Now let's touch back on Sector zero block 0 which is the manufacturer ID of the Integrated Circuit (IC). On older cards this is a 4 byte ID and on newer cards, its a 7 byte ID. I haven't found a good way to determine whether any particular card uses which length ID and the remaining bytes can be any sort of data the manufacturer wants to include. In any event, Sector 0, Block 0 is write protected.
Well, that brings us to the conclusion of this article. You should now know how to find and break down the Access Bits into what permissions they grant. Remember, each sector can have it's own KeyA, KeyB and Access Bits if you really want to get seriously secure (and complex). The vast majority of hotel key cards I've been able to play with use the same keys and access bits on each sector with data in it.
I guess one thing of note is that the data on the cards are encrypted with Crypto-1 which has been broken a number of years ago. However, the data you pull off a card with your Flipper One, provided you have all the keys, is decrypted already.