Skip to content

Reader BT Developer Documentation

This document describes the Bluetooth® Low Energy (BLE) interface to SPORTident Reader BT. It specifies services, characteristics, wire format, and the application-level request/response messages that are sent over the characteristics.

Terminology used within this document:

  • Reader: SPORTident Reader BT device
  • Client: The mobile/desktop app connecting to the reader
  • User: The person operating the client app, who may interact with the reader by inserting/removing cards, configuring settings, etc
  • SI-Card: SPORTident Card inserted into the reader
  • Service/Characteristic UUIDs: Defined for the SPORTident Reader BT
  • Message: An application payload written to / notified from a characteristic

Bluetooth Low Energy

BLE GATT (Generic Attribute Profile) defines how data is structured and exchanged between a BLE client and server.

  • A service groups related functionality (for example, device settings or card readout).
  • A characteristic inside a service contains a value and access properties (read, write, notify).
  • The client discovers services and characteristics after connection, then subscribes to notifications where required.
  • For Reader BT, requests are typically written by the client and responses are returned as notifications on the related characteristic.

In short: GATT provides the application-level data model on top of BLE, while this document specifies the exact UUIDs, message structure, and payload formats used by Reader BT.

Device Discovery

The reader must be in advertising mode, which is activated with the “Service/OFF” instruction card (see the Reader BT documentation).

The client then needs to scan for peripherals advertising the primary service UUID:

  • Primary service UUID used for scanning: bd510001-6aec-4628-a146-f3e95bc49e62
  • Note: The reader advertises the primary service UUID but not the card readout or backup service UUIDs, so scanning should target the primary service.
  • Note: BLE scanning is 20 seconds, which matches the time the reader remains in advertising mode.
  • Note: Depending on the platform/OS, additional filtering by device name prefix (e.g. “Reader BT”) may be possible and can help to reduce noise from non-reader devices.

Connecting

Connect to a discovered (or known) device by its BLE device ID (MAC address).

Depending on the BLE library and operating system used, a maximum MTU length (517) may be required.

After connecting, the client may validate that required services exist by enumerating services and checking UUIDs.

Services and Characteristics

Overview

All UUIDs below are 128-bit UUIDs. Reader BT UUIDs starts with the 32 bit identifier bd5100xx, where xx specifies the GATT service or characteristic.

Generally and unless stated otherwise: The client writes requests to a characteristic. The reader replies via a notification on the same characteristic (or a service-specific notify characteristic). All client > reader writes must be performed as Write With Response. (For the BLE uninitiated, Write With Response essentially means a write with an acknowledgement that is not visible at the application layer.)

A client should subscribe to the relevant services/characteristics:

  • Device settings and infos
    • Subscribe to the Read settings characteristic
  • Card data readout
    • Subscribe to the Card state characteristic
    • Subscribe to the Card data characteristic
  • Read data from the device memory
    • Subscribe to the Sessions characteristic

Settings service

Service for configuring device settings and requesting device information.

Service UUID: bd510001-6aec-4628-a146-f3e95bc49e62

Characteristics:

  • Read settings (bd510002)
    • Characteristic UUID: bd510002-6aec-4628-a146-f3e95bc49e62
    • Properties: Notify, Write With Response
    • Direction: bidirectional
    • Used for: reading device info, code number and other settings
  • Write settings (bd510003)
    • Characteristic UUID: bd510003-6aec-4628-a146-f3e95bc49e62
    • Properties: Write With Response, Write Without Response
    • Direction: Client > Reader
    • Used for: writing station configuration such as code number, sleep mode, etc

Card readout service

Service for reading data from an SI-Card.

Service UUID: bd510011-6aec-4628-a146-f3e95bc49e62

Characteristics:

  • Card state (bd510012)
    • Characteristic UUID: bd510012-6aec-4628-a146-f3e95bc49e62
    • Properties: Notify
    • Direction: Reader > Client (notifications)
    • Used for: card insert/remove state changes. If the station is in Auto Card Readout mode, a card insert notification triggers an automatic readout
  • Card data (bd510013)
    • Characteristic UUID: bd510013-6aec-4628-a146-f3e95bc49e62
    • Properties: Notify, Write With Response
    • Direction: bidirectional
    • Used for: readout requests, readout data (possibly segmented), and feedback commands.

Sessions service

A service for reading data from the device’s memory.

Service UUID: bd510031-6aec-4628-a146-f3e95bc49e62

Characteristics:

  • Sessions (bd510032)
    • Characteristic UUID: bd510032-6aec-4628-a146-f3e95bc49e62
    • Properties: Notify, Write With Response
    • Direction: bidirectional
    • Used for: session lookup table requests/responses and session data upload

Wire format

Message structure

All multi-byte integers are little-endian. Every message begins with a 4-byte header. The base message structure is:

OffsetSizeTypeNameDescription
02uint16message_idMessage ID (see below)
22uint16payload_lengthNumber of payload bytes following the header
4Nbyte[]payloadPayload bytes, length defined by payload_length

Use the message_id to identify the message type and decode the payload accordingly (see Messages).

Message segmentation

The BLE transport may deliver large payloads (notably card readout and backup transfers) split across multiple notifications. The client must support reassembly via a dedicated message, the wrapper message (message ID 0xA101) whose payload contains a segment of the original unsegmented message.

Wrapper message payload:

Offset (within payload)SizeTypeNameDescription
01uint8packet_flag0x01 first, 0x00 subsequentPacket, 0x02 last (SegmentMarker)

If packet_flag == 0x01 (First packet):

OffsetSizeTypeNameDescription
14uint32total_message_lengthExpected length (bytes) of the reassembled unsegmented message
5Nbyte[]segmentFirst segment bytes

If packet_flag == 0x00 (Continuation) or 0x02 (Last):

OffsetSizeTypeNameDescription
1Nbyte[]segmentSegment bytes

Reassembly rules:

  1. On First packet: clear buffer, store total_message_length, append segment.
  2. On SubsequentPacket: append segment.
  3. On Last: append segment, then buffer length MUST equal total_message_length.
  4. After successful reassembly: treat the reassembled bytes as a normal unsegmented message starting with the 4-byte base header.

Messages

Overview

This section defines payload layouts for the message IDs currently used by Reader BT. “Payload” below refers to bytes after the 4-byte base header (see Message structure).

The following table gives an overview of all defined messages:

NameMessage IDService/CharacteristicDirectionNotes
CardStateChange0x1101Card readout / Card stateReader > Client (notify)Card insert/remove events
CardDataReadoutMinimalData / CardDataReadoutCompleteData0x1102 / 0x1103Card readout / Card dataClient > Reader (write) + Reader > Client (notify)Minimal/complete card readout request/response
Feedback0x1110Card readout / Card dataClient > Reader (write)Trigger station feedback (LED/Buzzer)
ReadDeviceInfo0x010ESettings / Read settingsClient > Reader (write to Read settings) + Reader > Client (notify on Read settings)Request device information
ReadAllSettings0x010CSettings / Read settingsClient > Reader (write to Read settings) + Reader > Client (notify on Read settings)Request all station settings
WriteAllSettings0x010DSettings / Write settingsClient > Reader (write)Write all station settings
SetToSleepMode0x0101Settings / Write settingsClient > Reader (write)Put station to sleep mode
ReadAvailableSessionsRequest0x3101Sessions / SessionsClient > Reader (write)Request session lookup table page
ReadAvailableSessionsResponse0x3103Sessions / SessionsReader > Client (notify)Response with session lookup table page
ReadSessionDataRequest0x3102Sessions / SessionsClient > Reader (write)Request session data by session number
ReadSessionDataResponse0x3104Sessions / SessionsReader > Client (notify)Response with session data (may be segmented)

Card state change

  • Message ID: 0x1101
  • Characteristic: notify on Card state (bd510012)

4 byte message header, followed by 7 bytes payload :

OffsetSizeTypeNameNotes
04uint32card_numberSPORTident card number
41uint8state0 = Out, 1 = In
52uint16code_numberControl code number

Card readout

There are 2 messages for reading data from a card - minimal and complete. Minimal contains only the card number and punches. Complete contains information about the card owner and production information.

  • Minimal data message ID: 0x1102
  • Complete data message ID: 0x1103
  • Characteristic: notify on Card data (bd510013) (may be segmented)

4 byte message header, followed by payload :

Offset (from start of payload)SizeTypeNameNotes
04uint32card_number
41uint8card_familySee “Card family” below
52uint16punch_countNumber of punch records
7punch_count * 8struct[]punchesEach punch record is 8 bytes
7 + punches13 (optional)bytesSIAC_production_dataPresent only for complete + card_family = SIAC and 8000000 <= card_number < 9000000
variable (optional)bytesowner_dataPresent only for complete and if enough bytes remain; starts with 1 byte character_set and then NUL-terminated/padded string bytes

Punch record (8 bytes):

OffsetSizeTypeNameNotes
01uint8control_infoBit field used for beacon and radio mode (see decoding below)
11uint8punch_typeEncoded punch type
22uint16control_codeControl Code number
44uint32time_in_msMilliseconds in week (Sun 00:00:00 = 0)

control_info (uint8) decoding (Only for supported SPORTident cards (SIAC), others have the default value 0x00):

  • Bits 0..4 are reserved for future
  • Beacon mode - timing / punching mode flag:
    • if bit 5 set then punching mode used; by default timing mode (used also for direct punching)
  • Radio mode (2-bit enum in bits 6..7):
    • radio_mode = (control_type & 0xC0) >> 6
    • values :
      • 0 = No
      • 1 = Last
      • 2 = All
      • 3 = AllNew

Punch type values (uint8)

  • 0 = Undefined
  • 1 = Clear
  • 2 = Check
  • 3 = Start
  • 4 = StartReserve
  • 5 = Finish
  • 6 = FinishReserve
  • 7 = Control

The punch time is week-based and in milliseconds since Sunday morning 00:00:00.

Example:

  • time_in_ms = 183845000
  • day_index = floor(183845000 / 86400000) = 2 -> Tuesday (0 = Sunday, 1 = Monday, 2 = Tuesday)
  • time_of_day_ms = 183845000 % 86400000 = 11045000
  • 11,045,000 ms = 03:04:05.000

So 183845000 represents Tuesday 03:04:05.000.

Card family values (uint8):

  • 1 = SI-Card9
  • 2 = SI-Card8
  • 4 = SI-pCard
  • 15 = SIAC

The owner data is a string, terminated by 0x00. The data is separated by a semicolon ( ; ), the character set depends on character_set byte and possible codings are 1 (default) ISO8859-1 and 17 (ChineseSimplified) GB2312. The number of owner fields depends on the card family.

Owner data fields:

Field8/9SIAC/pCard
First nameXX
Last nameXX
Sex-X
Year of birth-X
Club-X
Email-X
Mobile-X
City-X
Street-X
Zip-X
Country-X

Owner data size (bytes) for complete readout:

  • SI-Card8: 104
  • SI-Card9: 24
  • SI-pCard or SIAC: 128

SIAC production data (13 bytes)

Present only for complete readout (message Id: 0x1103) when:

  • card_family = SIAC
  • 8000000 <= card_number < 9000000

Size: 13 bytes

Layout:

Offset (within SIAC_production_data)SizeTypeNameDescription
01uint8hw_version_rawHardware version; formatted as major.minor via hw_version_raw / 10 and hw_version_raw % 10
11uint8sw_version_rawSoftware version; formatted as major.minor via sw_version_raw / 10 and sw_version_raw % 10
22uint16signal_countFeedback cycle counter
42uint16clear_countClear counter
62uint16battery_mvBattery voltage in millivolts
81uint8battery_yearYears since 2000 (0 => 2000)
91uint8battery_month1..12
101uint8battery_day1..31
111uint8production_yearYears since 2000 (0 => 2000)
121uint8production_month1..12

Decoding notes:

  • battery_year and production_year are stored as years since 2000
  • Battery date is represented as a full date YYYY-MM-DD
  • Production date is represented as YYYY-MM

Feedback

The application can inform the user about the success of reading data. Currently, the Reader BT supports 2 feedback types: Feedback_Ok (short flash/beep), and Feedback_Error (longer flash/beep pattern). Feedback is triggered by writing a message with the corresponding feedback_type to the card data characteristic.

Feedback does not depend on whether the SI-Card is in the device or not.

  • Message ID: 0x1110
  • Characteristic: write to Card data (bd510013)

4 byte message header, followed by 1 byte payload:

OffsetSizeTypeName
01uint8feedback_type

feedback_type values:

  • 1 = Feedback_Ok - short flash/beep
  • 2 = Feedback_Error - longer flash/beep

Read device info

The response contains the values ​​of the Reader BT device - production date, serial number, etc.

To request device information, write message 0x010E to the Read settings (bd510002) characteristic with no payload (only 4-byte header).

Request:

  • Message ID: 0x010E
  • Characteristic: write to Read settings (bd510002)
  • Payload: (empty)

Response:

  • Message ID: 0x010E
  • Characteristic: notify on Read settings (bd510002)

4 byte message header, followed by payload layout:

OffsetSizeTypeNameNote
04uint32serial_number
42uint16device_typeDevice type identifier (e.g. 0x00A7)
62uint8[2]hw_version{ major, minor }
84structproduction_date{ year:uint16, month:uint8, day:uint8 }
124structbattery_date{ year:uint16, month:uint8, day:uint8 }
16variablebyte[]sw_version_asciiASCII, NUL-terminated / padded

Note: The Reader BT’s device type is 0x00A7 (167).

Read all settings

To request all Reader BT settings, write message 0x010C to the Read settings (bd510002) characteristic with no payload (only 4-byte header).

Request:

  • Message ID: 0x010C
  • Characteristic: write to Read settings (bd510002)
  • Payload: (empty)

Response:

  • Message ID: 0x010C
  • Characteristic: notify on Read settings (bd510002)

4 byte message header, 10 bytes payload layout:

OffsetSizeTypeNameNotes
02uint16code_numberControl number
21uint8auto_readBoolean - 1: Auto Card Readout is enabled in device
37reservedreservedReserved for future

Last 7 bytes are reserved for future use.

Write all settings

  • Message ID: 0x010D
  • Characteristic: write to Write settings (bd510003)

Method details:

  • Payload encoding matches Read all settings and uses the same layout as the read-all-settings response above.
  • The BLE transport uses Write With Response at the GATT level.

Read available sessions request

Reader BT memory is divided into sessions. A new session is created each time you connect. The last session is the current session.

The session table is like a circular buffer, a maximum of 291 sessions are stored in the buffer, older ones are overwritten.

The list of sessions is divided into pages, each page has maximum 5 records. Page 0 is the newest. To find out how many pages there are, read page 0 first.

  • Message ID: 0x3101
  • Characteristic: write to Sessions (bd510032)

4 byte message header, followed by 1 byte payload:

OffsetSizeTypeNameNotes
01uint8page_number0-based

Read available sessions response

  • Message ID: 0x3103
  • Characteristic: notify on Sessions (bd510032)

4 byte message header, payload header:

OffsetSizeTypeName
01uint8page_number
11uint8total_pages
21uint8entries_count

Then entries_count session entries follow.

Session lookup entry (20 bytes):

OffsetSizeTypeNameNotes
02uint16session_number
28uint64start_timeUnix time in seconds (or 0 as “unknown”)
108uint64end_timeUnix time in seconds (or duration in seconds when start_time == 0)
182uint16number_of_readouts

Read session data request

  • Message ID: 0x3102
  • Characteristic: write to Sessions (bd510032)

4 byte message header, payload:

OffsetSizeTypeName
02uint16session_number

Session number is obtained from the lookup table entries described above.

Read session data response

  • Message ID: 0x3104
  • Characteristic: notify on Sessions (bd510032) (may be segmented)

4 byte message header, payload header:

OffsetSizeTypeName
02uint16session_number
22uint16number_of_readouts
44uint32session_data_length

Then follows a concatenation of number_of_readouts embedded card readout messages, each encoded as:

  1. 4-byte base header (instruction + payload_length)
  2. payload_length bytes card readout payload

Each embedded readout’s message_id is expected to be either 0x1102 (minimal) or 0x1103 (complete).

  1. Scan for devices advertising the Reader BT’s Settings service UUID or device name, starting with “Reader BT”
  2. Connect to the selected device
  3. Subscribe to needed services
    • Settings for configuration/info
    • Card readout for live readout
    • Sessions for backup memory session download
  4. (Optional) Request device info, code number, and other settings
  5. For live readout
    • Wait for CardStateChange notification then request CardDataReadout
    • Optionally trigger feedback after successful CardDataReadout event
  6. For backup session download
    • Request lookup table page(s), then request session data