1# SPDX-License-Identifier: GPL-2.0-only 2# This file is part of Scapy 3# See https://scapy.net/ for more information 4# Copyright (C) Philippe Biondi <phil@secdev.org> 5# Copyright (C) Mike Ryan <mikeryan@lacklustre.net> 6# Copyright (C) Michael Farrell <micolous+git@gmail.com> 7# Copyright (C) Haram Park <freehr94@korea.ac.kr> 8 9""" 10Bluetooth layers, sockets and send/receive functions. 11""" 12 13import ctypes 14import functools 15import socket 16import struct 17import select 18from ctypes import sizeof 19 20from scapy.config import conf 21from scapy.data import ( 22 DLT_BLUETOOTH_HCI_H4, 23 DLT_BLUETOOTH_HCI_H4_WITH_PHDR, 24 DLT_BLUETOOTH_LINUX_MONITOR 25) 26from scapy.packet import bind_layers, Packet 27from scapy.fields import ( 28 BitField, 29 XBitField, 30 ByteEnumField, 31 ByteField, 32 FieldLenField, 33 FieldListField, 34 FlagsField, 35 IntField, 36 LEShortEnumField, 37 LEShortField, 38 LEIntField, 39 LenField, 40 MultipleTypeField, 41 NBytesField, 42 PacketListField, 43 PadField, 44 ShortField, 45 SignedByteField, 46 StrField, 47 StrFixedLenField, 48 StrLenField, 49 StrNullField, 50 UUIDField, 51 XByteField, 52 XLE3BytesField, 53 XLELongField, 54 XStrLenField, 55 XLEShortField, 56 XLEIntField, 57 LEMACField, 58 BitEnumField, 59) 60from scapy.supersocket import SuperSocket 61from scapy.sendrecv import sndrcv 62from scapy.data import MTU 63from scapy.consts import WINDOWS 64from scapy.error import warning 65 66 67############ 68# Consts # 69############ 70 71# From hci.h 72HCI_CHANNEL_RAW = 0 73HCI_CHANNEL_USER = 1 74HCI_CHANNEL_MONITOR = 2 75HCI_CHANNEL_CONTROL = 3 76HCI_CHANNEL_LOGGING = 4 77 78HCI_DEV_NONE = 0xffff 79 80 81########## 82# Layers # 83########## 84 85# See bluez/lib/hci.h for details 86 87# Transport layers 88 89class HCI_PHDR_Hdr(Packet): 90 name = "HCI PHDR transport layer" 91 fields_desc = [IntField("direction", 0)] 92 93 94# Real layers 95 96_bluetooth_packet_types = { 97 0: "Acknowledgement", 98 1: "Command", 99 2: "ACL Data", 100 3: "Synchronous", 101 4: "Event", 102 5: "Reserve", 103 14: "Vendor", 104 15: "Link Control" 105} 106 107_bluetooth_error_codes = { 108 0x00: "Success", 109 0x01: "Unknown HCI Command", 110 0x02: "Unknown Connection Identifier", 111 0x03: "Hardware Failure", 112 0x04: "Page Timeout", 113 0x05: "Authentication Failure", 114 0x06: "PIN or Key Missing", 115 0x07: "Memory Capacity Exceeded", 116 0x08: "Connection Timeout", 117 0x09: "Connection Limit Exceeded", 118 0x0A: "Synchronous Connection Limit To A Device Exceeded", 119 0x0B: "Connection Already Exists", 120 0x0C: "Command Disallowed", 121 0x0D: "Connection Rejected due to Limited Resources", 122 0x0E: "Connection Rejected Due To Security Reasons", 123 0x0F: "Connection Rejected due to Unacceptable BD_ADDR", 124 0x10: "Connection Accept Timeout Exceeded", 125 0x11: "Unsupported Feature or Parameter Value", 126 0x12: "Invalid HCI Command Parameters", 127 0x13: "Remote User Terminated Connection", 128 0x14: "Remote Device Terminated Connection due to Low Resources", 129 0x15: "Remote Device Terminated Connection due to Power Off", 130 0x16: "Connection Terminated By Local Host", 131 0x17: "Repeated Attempts", 132 0x18: "Pairing Not Allowed", 133 0x19: "Unknown LMP PDU", 134 0x1A: "Unsupported Remote Feature / Unsupported LMP Feature", 135 0x1B: "SCO Offset Rejected", 136 0x1C: "SCO Interval Rejected", 137 0x1D: "SCO Air Mode Rejected", 138 0x1E: "Invalid LMP Parameters / Invalid LL Parameters", 139 0x1F: "Unspecified Error", 140 0x20: "Unsupported LMP Parameter Value / Unsupported LL Parameter Value", 141 0x21: "Role Change Not Allowed", 142 0x22: "LMP Response Timeout / LL Response Timeout", 143 0x23: "LMP Error Transaction Collision / LL Procedure Collision", 144 0x24: "LMP PDU Not Allowed", 145 0x25: "Encryption Mode Not Acceptable", 146 0x26: "Link Key cannot be Changed", 147 0x27: "Requested QoS Not Supported", 148 0x28: "Instant Passed", 149 0x29: "Pairing With Unit Key Not Supported", 150 0x2A: "Different Transaction Collision", 151 0x2B: "Reserved for future use", 152 0x2C: "QoS Unacceptable Parameter", 153 0x2D: "QoS Rejected", 154 0x2E: "Channel Classification Not Supported", 155 0x2F: "Insufficient Security", 156 0x30: "Parameter Out Of Mandatory Range", 157 0x31: "Reserved for future use", 158 0x32: "Role Switch Pending", 159 0x33: "Reserved for future use", 160 0x34: "Reserved Slot Violation", 161 0x35: "Role Switch Failed", 162 0x36: "Extended Inquiry Response Too Large", 163 0x37: "Secure Simple Pairing Not Supported By Host", 164 0x38: "Host Busy - Pairing", 165 0x39: "Connection Rejected due to No Suitable Channel Found", 166 0x3A: "Controller Busy", 167 0x3B: "Unacceptable Connection Parameters", 168 0x3C: "Advertising Timeout", 169 0x3D: "Connection Terminated due to MIC Failure", 170 0x3E: "Connection Failed to be Established / Synchronization Timeout", 171 0x3F: "MAC Connection Failed", 172 0x40: "Coarse Clock Adjustment Rejected but Will Try to Adjust Using Clock" 173 " Dragging", 174 0x41: "Type0 Submap Not Defined", 175 0x42: "Unknown Advertising Identifier", 176 0x43: "Limit Reached", 177 0x44: "Operation Cancelled by Host", 178 0x45: "Packet Too Long" 179} 180 181_att_error_codes = { 182 0x01: "invalid handle", 183 0x02: "read not permitted", 184 0x03: "write not permitted", 185 0x04: "invalid pdu", 186 0x05: "insufficient auth", 187 0x06: "unsupported req", 188 0x07: "invalid offset", 189 0x08: "insufficient author", 190 0x09: "prepare queue full", 191 0x0a: "attr not found", 192 0x0b: "attr not long", 193 0x0c: "insufficient key size", 194 0x0d: "invalid value size", 195 0x0e: "unlikely", 196 0x0f: "insufficiet encrypt", 197 0x10: "unsupported gpr type", 198 0x11: "insufficient resources", 199} 200 201_bluetooth_features = [ 202 '3_slot_packets', 203 '5_slot_packets', 204 'encryption', 205 'slot_offset', 206 'timing_accuracy', 207 'role_switch', 208 'hold_mode', 209 'sniff_mode', 210 'park_mode', 211 'power_control_requests', 212 'channel_quality_driven_data_rate', 213 'sco_link', 214 'hv2_packets', 215 'hv3_packets', 216 'u_law_log_synchronous_data', 217 'a_law_log_synchronous_data', 218 'cvsd_synchronous_data', 219 'paging_parameter_negotiation', 220 'power_control', 221 'transparent_synchronous_data', 222 'flow_control_lag_4_bit0', 223 'flow_control_lag_4_bit1', 224 'flow_control_lag_4_bit2', 225 'broadband_encryption', 226 'cvsd_synchronous_data', 227 'edr_acl_2_mbps_mode', 228 'edr_acl_3_mbps_mode', 229 'enhanced_inquiry_scan', 230 'interlaced_inquiry_scan', 231 'interlaced_page_scan', 232 'rssi_with_inquiry_results', 233 'ev3_packets', 234 'ev4_packets', 235 'ev5_packets', 236 'reserved', 237 'afh_capable_slave', 238 'afh_classification_slave', 239 'br_edr_not_supported', 240 'le_supported_controller', 241 '3_slot_edr_acl_packets', 242 '5_slot_edr_acl_packets', 243 'sniff_subrating', 244 'pause_encryption', 245 'afh_capable_master', 246 'afh_classification_master', 247 'edr_esco_2_mbps_mode', 248 'edr_esco_3_mbps_mode', 249 '3_slot_edr_esco_packets', 250 'extended_inquiry_response', 251 'simultaneous_le_and_br_edr_to_same_device_capable_controller', 252 'reserved2', 253 'secure_simple_pairing', 254 'encapsulated_pdu', 255 'erroneous_data_reporting', 256 'non_flushable_packet_boundary_flag', 257 'reserved3', 258 'link_supervision_timeout_changed_event', 259 'inquiry_tx_power_level', 260 'enhanced_power_control', 261 'reserved4_bit0', 262 'reserved4_bit1', 263 'reserved4_bit2', 264 'reserved4_bit3', 265 'extended_features', 266] 267 268 269class HCI_Hdr(Packet): 270 name = "HCI header" 271 fields_desc = [ByteEnumField("type", 2, _bluetooth_packet_types)] 272 273 def mysummary(self): 274 return self.sprintf("HCI %type%") 275 276 277class HCI_ACL_Hdr(Packet): 278 name = "HCI ACL header" 279 fields_desc = [BitField("BC", 0, 2, tot_size=-2), 280 BitField("PB", 0, 2), 281 BitField("handle", 0, 12, end_tot_size=-2), 282 LEShortField("len", None), ] 283 284 def post_build(self, p, pay): 285 p += pay 286 if self.len is None: 287 p = p[:2] + struct.pack("<H", len(pay)) + p[4:] 288 return p 289 290 291class L2CAP_Hdr(Packet): 292 name = "L2CAP header" 293 fields_desc = [LEShortField("len", None), 294 LEShortEnumField("cid", 0, {1: "control", 4: "attribute"}), ] # noqa: E501 295 296 def post_build(self, p, pay): 297 p += pay 298 if self.len is None: 299 p = struct.pack("<H", len(pay)) + p[2:] 300 return p 301 302 303class L2CAP_CmdHdr(Packet): 304 name = "L2CAP command header" 305 fields_desc = [ 306 ByteEnumField("code", 8, {1: "rej", 307 2: "conn_req", 308 3: "conn_resp", 309 4: "conf_req", 310 5: "conf_resp", 311 6: "disconn_req", 312 7: "disconn_resp", 313 8: "echo_req", 314 9: "echo_resp", 315 10: "info_req", 316 11: "info_resp", 317 12: "create_channel_req", 318 13: "create_channel_resp", 319 14: "move_channel_req", 320 15: "move_channel_resp", 321 16: "move_channel_confirm_req", 322 17: "move_channel_confirm_resp", 323 18: "conn_param_update_req", 324 19: "conn_param_update_resp", 325 20: "LE_credit_based_conn_req", 326 21: "LE_credit_based_conn_resp", 327 22: "flow_control_credit_ind", 328 23: "credit_based_conn_req", 329 24: "credit_based_conn_resp", 330 25: "credit_based_reconf_req", 331 26: "credit_based_reconf_resp"}), 332 ByteField("id", 0), 333 LEShortField("len", None)] 334 335 def post_build(self, p, pay): 336 p += pay 337 if self.len is None: 338 p = p[:2] + struct.pack("<H", len(pay)) + p[4:] 339 return p 340 341 def answers(self, other): 342 if other.id == self.id: 343 if self.code == 1: 344 return 1 345 if other.code in [2, 4, 6, 8, 10, 18] and self.code == other.code + 1: # noqa: E501 346 if other.code == 8: 347 return 1 348 return self.payload.answers(other.payload) 349 return 0 350 351 352class L2CAP_ConnReq(Packet): 353 name = "L2CAP Conn Req" 354 fields_desc = [LEShortEnumField("psm", 0, {1: "SDP", 355 3: "RFCOMM", 356 5: "TCS-BIN", 357 7: "TCS-BIN-CORDLESS", 358 15: "BNEP", 359 17: "HID-Control", 360 19: "HID-Interrupt", 361 21: "UPnP", 362 23: "AVCTP-Control", 363 25: "AVDTP", 364 27: "AVCTP-Browsing", 365 29: "UDI_C-Plane", 366 31: "ATT", 367 33: "3DSP", 368 35: "IPSP", 369 37: "OTS"}), 370 LEShortField("scid", 0), 371 ] 372 373 374class L2CAP_ConnResp(Packet): 375 name = "L2CAP Conn Resp" 376 fields_desc = [LEShortField("dcid", 0), 377 LEShortField("scid", 0), 378 LEShortEnumField("result", 0, ["success", "pend", "cr_bad_psm", "cr_sec_block", "cr_no_mem", "reserved", "cr_inval_scid", "cr_scid_in_use"]), # noqa: E501 379 LEShortEnumField("status", 0, ["no_info", "authen_pend", "author_pend", "reserved"]), # noqa: E501 380 ] 381 382 def answers(self, other): 383 # dcid Resp == scid Req. Therefore compare SCIDs 384 return isinstance(other, L2CAP_ConnReq) and self.scid == other.scid 385 386 387class L2CAP_CmdRej(Packet): 388 name = "L2CAP Command Rej" 389 fields_desc = [LEShortField("reason", 0), 390 ] 391 392 393class L2CAP_ConfReq(Packet): 394 name = "L2CAP Conf Req" 395 fields_desc = [LEShortField("dcid", 0), 396 LEShortField("flags", 0), 397 ] 398 399 400class L2CAP_ConfResp(Packet): 401 name = "L2CAP Conf Resp" 402 fields_desc = [LEShortField("scid", 0), 403 LEShortField("flags", 0), 404 LEShortEnumField("result", 0, ["success", "unaccept", "reject", "unknown"]), # noqa: E501 405 ] 406 407 def answers(self, other): 408 # Req and Resp contain either the SCID or the DCID. 409 return isinstance(other, L2CAP_ConfReq) 410 411 412class L2CAP_DisconnReq(Packet): 413 name = "L2CAP Disconn Req" 414 fields_desc = [LEShortField("dcid", 0), 415 LEShortField("scid", 0), ] 416 417 418class L2CAP_DisconnResp(Packet): 419 name = "L2CAP Disconn Resp" 420 fields_desc = [LEShortField("dcid", 0), 421 LEShortField("scid", 0), ] 422 423 def answers(self, other): 424 return self.scid == other.scid 425 426 427class L2CAP_EchoReq(Packet): 428 name = "L2CAP Echo Req" 429 fields_desc = [StrField("data", ""), ] 430 431 432class L2CAP_EchoResp(Packet): 433 name = "L2CAP Echo Resp" 434 fields_desc = [StrField("data", ""), ] 435 436 437class L2CAP_InfoReq(Packet): 438 name = "L2CAP Info Req" 439 fields_desc = [LEShortEnumField("type", 0, {1: "CL_MTU", 2: "FEAT_MASK"}), 440 StrField("data", "") 441 ] 442 443 444class L2CAP_InfoResp(Packet): 445 name = "L2CAP Info Resp" 446 fields_desc = [LEShortField("type", 0), 447 LEShortEnumField("result", 0, ["success", "not_supp"]), 448 StrField("data", ""), ] 449 450 def answers(self, other): 451 return self.type == other.type 452 453 454class L2CAP_Create_Channel_Request(Packet): 455 name = "L2CAP Create Channel Request" 456 fields_desc = [LEShortEnumField("psm", 0, {1: "SDP", 457 3: "RFCOMM", 458 5: "TCS-BIN", 459 7: "TCS-BIN-CORDLESS", 460 15: "BNEP", 461 17: "HID-Control", 462 19: "HID-Interrupt", 463 21: "UPnP", 464 23: "AVCTP-Control", 465 25: "AVDTP", 466 27: "AVCTP-Browsing", 467 29: "UDI_C-Plane", 468 31: "ATT", 469 33: "3DSP", 470 35: "IPSP", 471 37: "OTS"}), 472 LEShortField("scid", 0), 473 ByteField("controller_id", 0), ] 474 475 476class L2CAP_Create_Channel_Response(Packet): 477 name = "L2CAP Create Channel Response" 478 fields_desc = [LEShortField("dcid", 0), 479 LEShortField("scid", 0), 480 LEShortEnumField("result", 0, { 481 0: "Connection successful", 482 1: "Connection pending", 483 2: "Connection refused - PSM not supported", 484 3: "Connection refused - security block", 485 4: "Connection refused - no resources available", 486 5: "Connection refused - cont_ID not supported", 487 6: "Connection refused - invalid scid", 488 7: "Connection refused - scid already allocated"}), 489 LEShortEnumField("status", 0, { 490 0: "No further information available", 491 1: "Authentication pending", 492 2: "Authorization pending"}), ] 493 494 495class L2CAP_Move_Channel_Request(Packet): 496 name = "L2CAP Move Channel Request" 497 fields_desc = [LEShortField("icid", 0), 498 ByteField("dest_controller_id", 0), ] 499 500 501class L2CAP_Move_Channel_Response(Packet): 502 name = "L2CAP Move Channel Response" 503 fields_desc = [LEShortField("icid", 0), 504 LEShortEnumField("result", 0, { 505 0: "Move success", 506 1: "Move pending", 507 2: "Move refused - Cont_ID not supported", 508 3: "Move refused - Cont_ID is same as old one", 509 4: "Move refused - Configuration not supported", 510 5: "Move refused - Move channel collision", 511 6: "Move refused - Not allowed to be moved"}), ] 512 513 514class L2CAP_Move_Channel_Confirmation_Request(Packet): 515 name = "L2CAP Move Channel Confirmation Request" 516 fields_desc = [LEShortField("icid", 0), 517 LEShortEnumField("result", 0, {0: "Move success", 518 1: "Move failure"}), ] 519 520 521class L2CAP_Move_Channel_Confirmation_Response(Packet): 522 name = "L2CAP Move Channel Confirmation Response" 523 fields_desc = [LEShortField("icid", 0), ] 524 525 526class L2CAP_Connection_Parameter_Update_Request(Packet): 527 name = "L2CAP Connection Parameter Update Request" 528 fields_desc = [LEShortField("min_interval", 0), 529 LEShortField("max_interval", 0), 530 LEShortField("slave_latency", 0), 531 LEShortField("timeout_mult", 0), ] 532 533 534class L2CAP_Connection_Parameter_Update_Response(Packet): 535 name = "L2CAP Connection Parameter Update Response" 536 fields_desc = [LEShortField("move_result", 0), ] 537 538 539class L2CAP_LE_Credit_Based_Connection_Request(Packet): 540 name = "L2CAP LE Credit Based Connection Request" 541 fields_desc = [LEShortField("spsm", 0), 542 LEShortField("scid", 0), 543 LEShortField("mtu", 0), 544 LEShortField("mps", 0), 545 LEShortField("initial_credits", 0), ] 546 547 548class L2CAP_LE_Credit_Based_Connection_Response(Packet): 549 name = "L2CAP LE Credit Based Connection Response" 550 fields_desc = [LEShortField("dcid", 0), 551 LEShortField("mtu", 0), 552 LEShortField("mps", 0), 553 LEShortField("initial_credits", 0), 554 LEShortEnumField("result", 0, { 555 0: "Connection successful", 556 2: "Connection refused - SPSM not supported", 557 4: "Connection refused - no resources available", 558 5: "Connection refused - authentication error", 559 6: "Connection refused - authorization error", 560 7: "Connection refused - encrypt_key size error", 561 8: "Connection refused - insufficient encryption", 562 9: "Connection refused - invalid scid", 563 10: "Connection refused - scid already allocated", 564 11: "Connection refused - parameters error"}), ] 565 566 567class L2CAP_Flow_Control_Credit_Ind(Packet): 568 name = "L2CAP Flow Control Credit Ind" 569 fields_desc = [LEShortField("cid", 0), 570 LEShortField("credits", 0), ] 571 572 573class L2CAP_Credit_Based_Connection_Request(Packet): 574 name = "L2CAP Credit Based Connection Request" 575 fields_desc = [LEShortField("spsm", 0), 576 LEShortField("mtu", 0), 577 LEShortField("mps", 0), 578 LEShortField("initial_credits", 0), 579 LEShortField("scid", 0), ] 580 581 582class L2CAP_Credit_Based_Connection_Response(Packet): 583 name = "L2CAP Credit Based Connection Response" 584 fields_desc = [LEShortField("mtu", 0), 585 LEShortField("mps", 0), 586 LEShortField("initial_credits", 0), 587 LEShortEnumField("result", 0, { 588 0: "All connection successful", 589 2: "All connection refused - SPSM not supported", 590 4: "Some connections refused - resources error", 591 5: "All connection refused - authentication error", 592 6: "All connection refused - authorization error", 593 7: "All connection refused - encrypt_key size error", 594 8: "All connection refused - encryption error", 595 9: "Some connection refused - invalid scid", 596 10: "Some connection refused - scid already allocated", 597 11: "All Connection refused - unacceptable parameters", 598 12: "All connections refused - invalid parameters"}), 599 LEShortField("dcid", 0), ] 600 601 602class L2CAP_Credit_Based_Reconfigure_Request(Packet): 603 name = "L2CAP Credit Based Reconfigure Request" 604 fields_desc = [LEShortField("mtu", 0), 605 LEShortField("mps", 0), 606 LEShortField("dcid", 0), ] 607 608 609class L2CAP_Credit_Based_Reconfigure_Response(Packet): 610 name = "L2CAP Credit Based Reconfigure Response" 611 fields_desc = [LEShortEnumField("result", 0, { 612 0: "Reconfig successful", 613 1: "Reconfig failed - MTU size reduction not allowed", 614 2: "Reconfig failed - MPS size reduction not allowed", 615 3: "Reconfig failed - one or more dcids invalid", 616 4: "Reconfig failed - unacceptable parameters"}), ] 617 618 619class ATT_Hdr(Packet): 620 name = "ATT header" 621 fields_desc = [XByteField("opcode", None), ] 622 623 624class ATT_Handle(Packet): 625 name = "ATT Short Handle" 626 fields_desc = [XLEShortField("handle", 0), 627 XLEShortField("value", 0)] 628 629 def extract_padding(self, s): 630 return b'', s 631 632 633class ATT_Handle_UUID128(Packet): 634 name = "ATT Handle (UUID 128)" 635 fields_desc = [XLEShortField("handle", 0), 636 UUIDField("value", None, uuid_fmt=UUIDField.FORMAT_REV)] 637 638 def extract_padding(self, s): 639 return b'', s 640 641 642class ATT_Error_Response(Packet): 643 name = "Error Response" 644 fields_desc = [XByteField("request", 0), 645 LEShortField("handle", 0), 646 ByteEnumField("ecode", 0, _att_error_codes), ] 647 648 649class ATT_Exchange_MTU_Request(Packet): 650 name = "Exchange MTU Request" 651 fields_desc = [LEShortField("mtu", 0), ] 652 653 654class ATT_Exchange_MTU_Response(Packet): 655 name = "Exchange MTU Response" 656 fields_desc = [LEShortField("mtu", 0), ] 657 658 659class ATT_Find_Information_Request(Packet): 660 name = "Find Information Request" 661 fields_desc = [XLEShortField("start", 0x0000), 662 XLEShortField("end", 0xffff), ] 663 664 665class ATT_Find_Information_Response(Packet): 666 name = "Find Information Response" 667 fields_desc = [ 668 XByteField("format", 1), 669 MultipleTypeField( 670 [ 671 (PacketListField("handles", [], ATT_Handle), 672 lambda pkt: pkt.format == 1), 673 (PacketListField("handles", [], ATT_Handle_UUID128), 674 lambda pkt: pkt.format == 2), 675 ], 676 StrFixedLenField("handles", "", length=0) 677 ) 678 ] 679 680 681class ATT_Find_By_Type_Value_Request(Packet): 682 name = "Find By Type Value Request" 683 fields_desc = [XLEShortField("start", 0x0001), 684 XLEShortField("end", 0xffff), 685 XLEShortField("uuid", None), 686 StrField("data", ""), ] 687 688 689class ATT_Find_By_Type_Value_Response(Packet): 690 name = "Find By Type Value Response" 691 fields_desc = [PacketListField("handles", [], ATT_Handle)] 692 693 694class ATT_Read_By_Type_Request_128bit(Packet): 695 name = "Read By Type Request" 696 fields_desc = [XLEShortField("start", 0x0001), 697 XLEShortField("end", 0xffff), 698 XLELongField("uuid1", None), 699 XLELongField("uuid2", None)] 700 701 @classmethod 702 def dispatch_hook(cls, _pkt=None, *args, **kargs): 703 if _pkt and len(_pkt) == 6: 704 return ATT_Read_By_Type_Request 705 return ATT_Read_By_Type_Request_128bit 706 707 708class ATT_Read_By_Type_Request(Packet): 709 name = "Read By Type Request" 710 fields_desc = [XLEShortField("start", 0x0001), 711 XLEShortField("end", 0xffff), 712 XLEShortField("uuid", None)] 713 714 715class ATT_Handle_Variable(Packet): 716 __slots__ = ["val_length"] 717 fields_desc = [XLEShortField("handle", 0), 718 XStrLenField( 719 "value", 0, 720 length_from=lambda pkt: pkt.val_length)] 721 722 def __init__(self, _pkt=b"", val_length=2, **kwargs): 723 self.val_length = val_length 724 Packet.__init__(self, _pkt, **kwargs) 725 726 def extract_padding(self, s): 727 return b"", s 728 729 730class ATT_Read_By_Type_Response(Packet): 731 name = "Read By Type Response" 732 fields_desc = [ByteField("len", 4), 733 PacketListField( 734 "handles", [], 735 next_cls_cb=lambda pkt, *args: ( 736 pkt._next_cls_cb(pkt, *args) 737 ))] 738 739 @classmethod 740 def _next_cls_cb(cls, pkt, lst, p, remain): 741 if len(remain) >= pkt.len: 742 return functools.partial( 743 ATT_Handle_Variable, 744 val_length=pkt.len - 2 745 ) 746 return None 747 748 749class ATT_Read_Request(Packet): 750 name = "Read Request" 751 fields_desc = [XLEShortField("gatt_handle", 0), ] 752 753 754class ATT_Read_Response(Packet): 755 name = "Read Response" 756 fields_desc = [StrField("value", "")] 757 758 759class ATT_Read_Multiple_Request(Packet): 760 name = "Read Multiple Request" 761 fields_desc = [FieldListField("handles", [], XLEShortField("", 0))] 762 763 764class ATT_Read_Multiple_Response(Packet): 765 name = "Read Multiple Response" 766 fields_desc = [StrField("values", "")] 767 768 769class ATT_Read_By_Group_Type_Request(Packet): 770 name = "Read By Group Type Request" 771 fields_desc = [XLEShortField("start", 0), 772 XLEShortField("end", 0xffff), 773 XLEShortField("uuid", 0), ] 774 775 776class ATT_Read_By_Group_Type_Response(Packet): 777 name = "Read By Group Type Response" 778 fields_desc = [XByteField("length", 0), 779 StrField("data", ""), ] 780 781 782class ATT_Write_Request(Packet): 783 name = "Write Request" 784 fields_desc = [XLEShortField("gatt_handle", 0), 785 StrField("data", ""), ] 786 787 788class ATT_Write_Command(Packet): 789 name = "Write Request" 790 fields_desc = [XLEShortField("gatt_handle", 0), 791 StrField("data", ""), ] 792 793 794class ATT_Write_Response(Packet): 795 name = "Write Response" 796 797 798class ATT_Prepare_Write_Request(Packet): 799 name = "Prepare Write Request" 800 fields_desc = [ 801 XLEShortField("gatt_handle", 0), 802 LEShortField("offset", 0), 803 StrField("data", "") 804 ] 805 806 807class ATT_Prepare_Write_Response(ATT_Prepare_Write_Request): 808 name = "Prepare Write Response" 809 810 811class ATT_Handle_Value_Notification(Packet): 812 name = "Handle Value Notification" 813 fields_desc = [XLEShortField("gatt_handle", 0), 814 StrField("value", ""), ] 815 816 817class ATT_Execute_Write_Request(Packet): 818 name = "Execute Write Request" 819 fields_desc = [ 820 ByteEnumField("flags", 1, { 821 0: "Cancel all prepared writes", 822 1: "Immediately write all pending prepared values", 823 }), 824 ] 825 826 827class ATT_Execute_Write_Response(Packet): 828 name = "Execute Write Response" 829 830 831class ATT_Read_Blob_Request(Packet): 832 name = "Read Blob Request" 833 fields_desc = [ 834 XLEShortField("gatt_handle", 0), 835 LEShortField("offset", 0) 836 ] 837 838 839class ATT_Read_Blob_Response(Packet): 840 name = "Read Blob Response" 841 fields_desc = [ 842 StrField("value", "") 843 ] 844 845 846class ATT_Handle_Value_Indication(Packet): 847 name = "Handle Value Indication" 848 fields_desc = [ 849 XLEShortField("gatt_handle", 0), 850 StrField("value", ""), 851 ] 852 853 854class SM_Hdr(Packet): 855 name = "SM header" 856 fields_desc = [ByteField("sm_command", None)] 857 858 859class SM_Pairing_Request(Packet): 860 name = "Pairing Request" 861 fields_desc = [ByteEnumField("iocap", 3, {0: "DisplayOnly", 1: "DisplayYesNo", 2: "KeyboardOnly", 3: "NoInputNoOutput", 4: "KeyboardDisplay"}), # noqa: E501 862 ByteEnumField("oob", 0, {0: "Not Present", 1: "Present (from remote device)"}), # noqa: E501 863 BitField("authentication", 0, 8), 864 ByteField("max_key_size", 16), 865 ByteField("initiator_key_distribution", 0), 866 ByteField("responder_key_distribution", 0), ] 867 868 869class SM_Pairing_Response(Packet): 870 name = "Pairing Response" 871 fields_desc = [ByteEnumField("iocap", 3, {0: "DisplayOnly", 1: "DisplayYesNo", 2: "KeyboardOnly", 3: "NoInputNoOutput", 4: "KeyboardDisplay"}), # noqa: E501 872 ByteEnumField("oob", 0, {0: "Not Present", 1: "Present (from remote device)"}), # noqa: E501 873 BitField("authentication", 0, 8), 874 ByteField("max_key_size", 16), 875 ByteField("initiator_key_distribution", 0), 876 ByteField("responder_key_distribution", 0), ] 877 878 879class SM_Confirm(Packet): 880 name = "Pairing Confirm" 881 fields_desc = [StrFixedLenField("confirm", b'\x00' * 16, 16)] 882 883 884class SM_Random(Packet): 885 name = "Pairing Random" 886 fields_desc = [StrFixedLenField("random", b'\x00' * 16, 16)] 887 888 889class SM_Failed(Packet): 890 name = "Pairing Failed" 891 fields_desc = [XByteField("reason", 0)] 892 893 894class SM_Encryption_Information(Packet): 895 name = "Encryption Information" 896 fields_desc = [StrFixedLenField("ltk", b"\x00" * 16, 16), ] 897 898 899class SM_Master_Identification(Packet): 900 name = "Master Identification" 901 fields_desc = [XLEShortField("ediv", 0), 902 StrFixedLenField("rand", b'\x00' * 8, 8), ] 903 904 905class SM_Identity_Information(Packet): 906 name = "Identity Information" 907 fields_desc = [StrFixedLenField("irk", b'\x00' * 16, 16), ] 908 909 910class SM_Identity_Address_Information(Packet): 911 name = "Identity Address Information" 912 fields_desc = [ByteEnumField("atype", 0, {0: "public"}), 913 LEMACField("address", None), ] 914 915 916class SM_Signing_Information(Packet): 917 name = "Signing Information" 918 fields_desc = [StrFixedLenField("csrk", b'\x00' * 16, 16), ] 919 920 921class SM_Public_Key(Packet): 922 name = "Public Key" 923 fields_desc = [StrFixedLenField("key_x", b'\x00' * 32, 32), 924 StrFixedLenField("key_y", b'\x00' * 32, 32), ] 925 926 927class SM_DHKey_Check(Packet): 928 name = "DHKey Check" 929 fields_desc = [StrFixedLenField("dhkey_check", b'\x00' * 16, 16), ] 930 931 932class EIR_Hdr(Packet): 933 name = "EIR Header" 934 fields_desc = [ 935 LenField("len", None, fmt="B", adjust=lambda x: x + 1), # Add bytes mark # noqa: E501 936 # https://www.bluetooth.com/specifications/assigned-numbers/generic-access-profile 937 ByteEnumField("type", 0, { 938 0x01: "flags", 939 0x02: "incomplete_list_16_bit_svc_uuids", 940 0x03: "complete_list_16_bit_svc_uuids", 941 0x04: "incomplete_list_32_bit_svc_uuids", 942 0x05: "complete_list_32_bit_svc_uuids", 943 0x06: "incomplete_list_128_bit_svc_uuids", 944 0x07: "complete_list_128_bit_svc_uuids", 945 0x08: "shortened_local_name", 946 0x09: "complete_local_name", 947 0x0a: "tx_power_level", 948 0x0d: "class_of_device", 949 0x0e: "simple_pairing_hash", 950 0x0f: "simple_pairing_rand", 951 952 0x10: "sec_mgr_tk", 953 0x11: "sec_mgr_oob_flags", 954 0x12: "slave_conn_intvl_range", 955 0x14: "list_16_bit_svc_sollication_uuids", 956 0x15: "list_128_bit_svc_sollication_uuids", 957 0x16: "svc_data_16_bit_uuid", 958 0x17: "pub_target_addr", 959 0x18: "rand_target_addr", 960 0x19: "appearance", 961 0x1a: "adv_intvl", 962 0x1b: "le_addr", 963 0x1c: "le_role", 964 0x1d: "simple_pairing_hash_256", 965 0x1e: "simple_pairing_rand_256", 966 0x1f: "list_32_bit_svc_sollication_uuids", 967 968 0x20: "svc_data_32_bit_uuid", 969 0x21: "svc_data_128_bit_uuid", 970 0x22: "sec_conn_confirm", 971 0x23: "sec_conn_rand", 972 0x24: "uri", 973 0x25: "indoor_positioning", 974 0x26: "transport_discovery", 975 0x27: "le_supported_features", 976 0x28: "channel_map_update", 977 0x29: "mesh_pb_adv", 978 0x2a: "mesh_message", 979 0x2b: "mesh_beacon", 980 981 0x3d: "3d_information", 982 983 0xff: "mfg_specific_data", 984 }), 985 ] 986 987 def mysummary(self): 988 return self.sprintf("EIR %type%") 989 990 def guess_payload_class(self, payload): 991 if self.len == 0: 992 # For Extended_Inquiry_Response, stop when len=0 993 return conf.padding_layer 994 return super(EIR_Hdr, self).guess_payload_class(payload) 995 996 997class EIR_Element(Packet): 998 name = "EIR Element" 999 1000 def extract_padding(self, s): 1001 # Needed to end each EIR_Element packet and make PacketListField work. 1002 return b'', s 1003 1004 @staticmethod 1005 def length_from(pkt): 1006 if not pkt.underlayer: 1007 warning("Missing an upper-layer") 1008 return 0 1009 # 'type' byte is included in the length, so subtract 1: 1010 return pkt.underlayer.len - 1 1011 1012 1013class EIR_Raw(EIR_Element): 1014 name = "EIR Raw" 1015 fields_desc = [ 1016 StrLenField("data", "", length_from=EIR_Element.length_from) 1017 ] 1018 1019 1020class EIR_Flags(EIR_Element): 1021 name = "Flags" 1022 fields_desc = [ 1023 FlagsField("flags", 0x2, 8, 1024 ["limited_disc_mode", "general_disc_mode", 1025 "br_edr_not_supported", "simul_le_br_edr_ctrl", 1026 "simul_le_br_edr_host"] + 3 * ["reserved"]) 1027 ] 1028 1029 1030class EIR_CompleteList16BitServiceUUIDs(EIR_Element): 1031 name = "Complete list of 16-bit service UUIDs" 1032 fields_desc = [ 1033 # https://www.bluetooth.com/specifications/assigned-numbers/16-bit-uuids-for-members 1034 FieldListField("svc_uuids", None, XLEShortField("uuid", 0), 1035 length_from=EIR_Element.length_from) 1036 ] 1037 1038 1039class EIR_IncompleteList16BitServiceUUIDs(EIR_CompleteList16BitServiceUUIDs): 1040 name = "Incomplete list of 16-bit service UUIDs" 1041 1042 1043class EIR_CompleteList32BitServiceUUIDs(EIR_Element): 1044 name = 'Complete list of 32-bit service UUIDs' 1045 fields_desc = [ 1046 # https://www.bluetooth.com/specifications/assigned-numbers 1047 FieldListField('svc_uuids', None, XLEIntField('uuid', 0), 1048 length_from=EIR_Element.length_from) 1049 ] 1050 1051 1052class EIR_IncompleteList32BitServiceUUIDs(EIR_CompleteList32BitServiceUUIDs): 1053 name = 'Incomplete list of 32-bit service UUIDs' 1054 1055 1056class EIR_CompleteList128BitServiceUUIDs(EIR_Element): 1057 name = "Complete list of 128-bit service UUIDs" 1058 fields_desc = [ 1059 FieldListField("svc_uuids", None, 1060 UUIDField("uuid", None, uuid_fmt=UUIDField.FORMAT_REV), 1061 length_from=EIR_Element.length_from) 1062 ] 1063 1064 1065class EIR_IncompleteList128BitServiceUUIDs(EIR_CompleteList128BitServiceUUIDs): 1066 name = "Incomplete list of 128-bit service UUIDs" 1067 1068 1069class EIR_CompleteLocalName(EIR_Element): 1070 name = "Complete Local Name" 1071 fields_desc = [ 1072 StrLenField("local_name", "", length_from=EIR_Element.length_from) 1073 ] 1074 1075 1076class EIR_ShortenedLocalName(EIR_CompleteLocalName): 1077 name = "Shortened Local Name" 1078 1079 1080class EIR_TX_Power_Level(EIR_Element): 1081 name = "TX Power Level" 1082 fields_desc = [SignedByteField("level", 0)] 1083 1084 1085class EIR_ClassOfDevice(EIR_Element): 1086 name = 'Class of device' 1087 fields_desc = [ 1088 FlagsField('major_service_classes', 0, 11, [ 1089 'limited_discoverable_mode', 1090 'le_audio', 1091 'reserved', 1092 'positioning', 1093 'networking', 1094 'rendering', 1095 'capturing', 1096 'object_transfer', 1097 'audio', 1098 'telephony', 1099 'information' 1100 ], tot_size=-3), 1101 BitEnumField('major_device_class', 0, 5, { 1102 0x00: 'miscellaneous', 1103 0x01: 'computer', 1104 0x02: 'phone', 1105 0x03: 'lan', 1106 0x04: 'audio_video', 1107 0x05: 'peripheral', 1108 0x06: 'imaging', 1109 0x07: 'wearable', 1110 0x08: 'toy', 1111 0x09: 'health', 1112 0x1f: 'uncategorized' 1113 }), 1114 BitField('minor_device_class', 0, 6), 1115 BitField('fixed', 0, 2, end_tot_size=-3) 1116 ] 1117 1118 1119class EIR_SecureSimplePairingHashC192(EIR_Element): 1120 name = 'Secure Simple Pairing Hash C-192' 1121 fields_desc = [NBytesField('hash', 0, 16)] 1122 1123 1124class EIR_SecureSimplePairingRandomizerR192(EIR_Element): 1125 name = 'Secure Simple Pairing Randomizer R-192' 1126 fields_desc = [NBytesField('randomizer', 0, 16)] 1127 1128 1129class EIR_SecurityManagerOOBFlags(EIR_Element): 1130 name = 'Security Manager Out of Band Flags' 1131 fields_desc = [ 1132 BitField('oob_flags_field', 0, 1), 1133 BitField('le_supported', 0, 1), 1134 BitField('previously_used', 0, 1), 1135 BitField('address_type', 0, 1), 1136 BitField('reserved', 0, 4) 1137 ] 1138 1139 1140class EIR_PeripheralConnectionIntervalRange(EIR_Element): 1141 name = 'Peripheral Connection Interval Range' 1142 fields_desc = [ 1143 LEShortField('conn_interval_min', 0xFFFF), 1144 LEShortField('conn_interval_max', 0xFFFF) 1145 ] 1146 1147 1148class EIR_Manufacturer_Specific_Data(EIR_Element): 1149 name = "EIR Manufacturer Specific Data" 1150 fields_desc = [ 1151 # https://www.bluetooth.com/specifications/assigned-numbers/company-identifiers 1152 XLEShortField("company_id", None), 1153 ] 1154 1155 registered_magic_payloads = {} 1156 1157 @classmethod 1158 def register_magic_payload(cls, payload_cls, magic_check=None): 1159 """ 1160 Registers a payload type that uses magic data. 1161 1162 Traditional payloads require registration of a Bluetooth Company ID 1163 (requires company membership of the Bluetooth SIG), or a Bluetooth 1164 Short UUID (requires a once-off payment). 1165 1166 There are alternatives which don't require registration (such as 1167 128-bit UUIDs), but the biggest consumer of energy in a beacon is the 1168 radio -- so the energy consumption of a beacon is proportional to the 1169 number of bytes in a beacon frame. 1170 1171 Some beacon formats side-step this issue by using the Company ID of 1172 their beacon hardware manufacturer, and adding a "magic data sequence" 1173 at the start of the Manufacturer Specific Data field. 1174 1175 Examples of this are AltBeacon and GeoBeacon. 1176 1177 For an example of this method in use, see ``scapy.contrib.altbeacon``. 1178 1179 :param Type[scapy.packet.Packet] payload_cls: 1180 A reference to a Packet subclass to register as a payload. 1181 :param Callable[[bytes], bool] magic_check: 1182 (optional) callable to use to if a payload should be associated 1183 with this type. If not supplied, ``payload_cls.magic_check`` is 1184 used instead. 1185 :raises TypeError: If ``magic_check`` is not specified, 1186 and ``payload_cls.magic_check`` is not implemented. 1187 """ 1188 if magic_check is None: 1189 if hasattr(payload_cls, "magic_check"): 1190 magic_check = payload_cls.magic_check 1191 else: 1192 raise TypeError("magic_check not specified, and {} has no " 1193 "attribute magic_check".format(payload_cls)) 1194 1195 cls.registered_magic_payloads[payload_cls] = magic_check 1196 1197 def default_payload_class(self, payload): 1198 for cls, check in ( 1199 EIR_Manufacturer_Specific_Data.registered_magic_payloads.items() 1200 ): 1201 if check(payload): 1202 return cls 1203 1204 return Packet.default_payload_class(self, payload) 1205 1206 def extract_padding(self, s): 1207 # Needed to end each EIR_Element packet and make PacketListField work. 1208 plen = EIR_Element.length_from(self) - 2 1209 return s[:plen], s[plen:] 1210 1211 1212class EIR_Device_ID(EIR_Element): 1213 name = "Device ID" 1214 fields_desc = [ 1215 XLEShortField("vendor_id_source", 0), 1216 XLEShortField("vendor_id", 0), 1217 XLEShortField("product_id", 0), 1218 XLEShortField("version", 0), 1219 ] 1220 1221 1222class EIR_ServiceData16BitUUID(EIR_Element): 1223 name = "EIR Service Data - 16-bit UUID" 1224 fields_desc = [ 1225 # https://www.bluetooth.com/specifications/assigned-numbers/16-bit-uuids-for-members 1226 XLEShortField("svc_uuid", None), 1227 ] 1228 1229 def extract_padding(self, s): 1230 # Needed to end each EIR_Element packet and make PacketListField work. 1231 plen = EIR_Element.length_from(self) - 2 1232 return s[:plen], s[plen:] 1233 1234 1235class EIR_ServiceData32BitUUID(EIR_Element): 1236 name = 'EIR Service Data - 32-bit UUID' 1237 fields_desc = [ 1238 XLEIntField('svc_uuid', 0), 1239 ] 1240 1241 def extract_padding(self, s): 1242 # Needed to end each EIR_Element packet and make PacketListField work. 1243 plen = EIR_Element.length_from(self) - 4 1244 return s[:plen], s[plen:] 1245 1246 1247class EIR_ServiceData128BitUUID(EIR_Element): 1248 name = 'EIR Service Data - 128-bit UUID' 1249 fields_desc = [ 1250 UUIDField('svc_uuid', None, uuid_fmt=UUIDField.FORMAT_REV) 1251 ] 1252 1253 def extract_padding(self, s): 1254 # Needed to end each EIR_Element packet and make PacketListField work. 1255 plen = EIR_Element.length_from(self) - 16 1256 return s[:plen], s[plen:] 1257 1258 1259class HCI_Command_Hdr(Packet): 1260 name = "HCI Command header" 1261 fields_desc = [XBitField("ogf", 0, 6, tot_size=-2), 1262 XBitField("ocf", 0, 10, end_tot_size=-2), 1263 LenField("len", None, fmt="B"), ] 1264 1265 def answers(self, other): 1266 return False 1267 1268 @property 1269 def opcode(self): 1270 return (self.ogf << 10) + self.ocf 1271 1272 def post_build(self, p, pay): 1273 p += pay 1274 if self.len is None: 1275 p = p[:2] + struct.pack("B", len(pay)) + p[3:] 1276 return p 1277 1278 1279# BUETOOTH CORE SPECIFICATION 5.4 | Vol 3, Part C 1280# 8 EXTENDED INQUIRY RESPONSE 1281 1282class HCI_Extended_Inquiry_Response(Packet): 1283 fields_desc = [ 1284 PadField( 1285 PacketListField( 1286 "eir_data", [], 1287 next_cls_cb=lambda *args: ( 1288 (not args[2] or args[2].len != 0) and EIR_Hdr or conf.raw_layer 1289 ) 1290 ), 1291 align=31, padwith=b"\0", 1292 ), 1293 ] 1294 1295 1296# BLUETOOTH CORE SPECIFICATION Version 5.4 | Vol 4, Part E 1297# 7 HCI COMMANDS AND EVENTS 1298# 7.1 LINK CONTROL COMMANDS, the OGF is defined as 0x01 1299 1300class HCI_Cmd_Inquiry(Packet): 1301 """ 1302 7.1.1 Inquiry command 1303 """ 1304 name = "HCI_Inquiry" 1305 fields_desc = [XLE3BytesField("lap", 0x9E8B33), 1306 ByteField("inquiry_length", 0), 1307 ByteField("num_responses", 0)] 1308 1309 1310class HCI_Cmd_Inquiry_Cancel(Packet): 1311 """ 1312 7.1.2 Inquiry Cancel command 1313 """ 1314 name = "HCI_Inquiry_Cancel" 1315 1316 1317class HCI_Cmd_Periodic_Inquiry_Mode(Packet): 1318 """ 1319 7.1.3 Periodic Inquiry Mode command 1320 """ 1321 name = "HCI_Periodic_Inquiry_Mode" 1322 fields_desc = [LEShortField("max_period_length", 0x0003), 1323 LEShortField("min_period_length", 0x0002), 1324 XLE3BytesField("lap", 0x9E8B33), 1325 ByteField("inquiry_length", 0), 1326 ByteField("num_responses", 0)] 1327 1328 1329class HCI_Cmd_Exit_Peiodic_Inquiry_Mode(Packet): 1330 """ 1331 7.1.4 Exit Periodic Inquiry Mode command 1332 """ 1333 name = "HCI_Exit_Periodic_Inquiry_Mode" 1334 1335 1336class HCI_Cmd_Create_Connection(Packet): 1337 """ 1338 7.1.5 Create Connection command 1339 """ 1340 name = "HCI_Create_Connection" 1341 fields_desc = [LEMACField("bd_addr", None), 1342 LEShortField("packet_type", 0xcc18), 1343 ByteField("page_scan_repetition_mode", 0x02), 1344 ByteField("reserved", 0x0), 1345 LEShortField("clock_offset", 0x0), 1346 ByteField("allow_role_switch", 0x1), ] 1347 1348 1349class HCI_Cmd_Disconnect(Packet): 1350 """ 1351 7.1.6 Disconnect command 1352 """ 1353 name = "HCI_Disconnect" 1354 fields_desc = [XLEShortField("handle", 0), 1355 ByteField("reason", 0x13), ] 1356 1357 1358class HCI_Cmd_Create_Connection_Cancel(Packet): 1359 """ 1360 7.1.7 Create Connection Cancel command 1361 """ 1362 name = "HCI_Create_Connection_Cancel" 1363 fields_desc = [LEMACField("bd_addr", None), ] 1364 1365 1366class HCI_Cmd_Accept_Connection_Request(Packet): 1367 """ 1368 7.1.8 Accept Connection Request command 1369 """ 1370 name = "HCI_Accept_Connection_Request" 1371 fields_desc = [LEMACField("bd_addr", None), 1372 ByteField("role", 0x1), ] 1373 1374 1375class HCI_Cmd_Reject_Connection_Response(Packet): 1376 """ 1377 7.1.9 Reject Connection Request command 1378 """ 1379 name = "HCI_Reject_Connection_Response" 1380 fields_desc = [LEMACField("bd_addr", None), 1381 ByteField("reason", 0x1), ] 1382 1383 1384class HCI_Cmd_Link_Key_Request_Reply(Packet): 1385 """ 1386 7.1.10 Link Key Request Reply command 1387 """ 1388 name = "HCI_Link_Key_Request_Reply" 1389 fields_desc = [LEMACField("bd_addr", None), 1390 NBytesField("link_key", None, 16), ] 1391 1392 1393class HCI_Cmd_Link_Key_Request_Negative_Reply(Packet): 1394 """ 1395 7.1.11 Link Key Request Negative Reply command 1396 """ 1397 name = "HCI_Link_Key_Request_Negative_Reply" 1398 fields_desc = [LEMACField("bd_addr", None), ] 1399 1400 1401class HCI_Cmd_PIN_Code_Request_Reply(Packet): 1402 """ 1403 7.1.12 PIN Code Request Reply command 1404 """ 1405 name = "HCI_PIN_Code_Request_Reply" 1406 fields_desc = [LEMACField("bd_addr", None), 1407 ByteField("pin_code_length", 7), 1408 NBytesField("pin_code", b"\x00" * 16, sz=16), ] 1409 1410 1411class HCI_Cmd_PIN_Code_Request_Negative_Reply(Packet): 1412 """ 1413 7.1.13 PIN Code Request Negative Reply command 1414 """ 1415 name = "HCI_PIN_Code_Request_Negative_Reply" 1416 fields_desc = [LEMACField("bd_addr", None), ] 1417 1418 1419class HCI_Cmd_Change_Connection_Packet_Type(Packet): 1420 """ 1421 7.1.14 Change Connection Packet Type command 1422 """ 1423 name = "HCI_Cmd_Change_Connection_Packet_Type" 1424 fields_desc = [XLEShortField("connection_handle", None), 1425 LEShortField("packet_type", 0), ] 1426 1427 1428class HCI_Cmd_Authentication_Requested(Packet): 1429 """ 1430 7.1.15 Authentication Requested command 1431 """ 1432 name = "HCI_Authentication_Requested" 1433 fields_desc = [LEShortField("handle", 0)] 1434 1435 1436class HCI_Cmd_Set_Connection_Encryption(Packet): 1437 """ 1438 7.1.16 Set Connection Encryption command 1439 """ 1440 name = "HCI_Set_Connection_Encryption" 1441 fields_desc = [LEShortField("handle", 0), ByteField("encryption_enable", 0)] 1442 1443 1444class HCI_Cmd_Change_Connection_Link_Key(Packet): 1445 """ 1446 7.1.17 Change Connection Link Key command 1447 """ 1448 name = "HCI_Change_Connection_Link_Key" 1449 fields_desc = [LEShortField("handle", 0), ] 1450 1451 1452class HCI_Cmd_Link_Key_Selection(Packet): 1453 """ 1454 7.1.18 Change Connection Link Key command 1455 """ 1456 name = "HCI_Cmd_Link_Key_Selection" 1457 fields_desc = [ByteEnumField("handle", 0, {0: "Use semi-permanent Link Keys", 1458 1: "Use Temporary Link Key", }), ] 1459 1460 1461class HCI_Cmd_Remote_Name_Request(Packet): 1462 """ 1463 7.1.19 Remote Name Request command 1464 """ 1465 name = "HCI_Remote_Name_Request" 1466 fields_desc = [LEMACField("bd_addr", None), 1467 ByteField("page_scan_repetition_mode", 0x02), 1468 ByteField("reserved", 0x0), 1469 LEShortField("clock_offset", 0x0), ] 1470 1471 1472class HCI_Cmd_Remote_Name_Request_Cancel(Packet): 1473 """ 1474 7.1.20 Remote Name Request Cancel command 1475 """ 1476 name = "HCI_Remote_Name_Request_Cancel" 1477 fields_desc = [LEMACField("bd_addr", None), ] 1478 1479 1480class HCI_Cmd_Read_Remote_Supported_Features(Packet): 1481 """ 1482 7.1.21 Read Remote Supported Features command 1483 """ 1484 name = "HCI_Read_Remote_Supported_Features" 1485 fields_desc = [LEShortField("connection_handle", None), ] 1486 1487 1488class HCI_Cmd_Read_Remote_Extended_Features(Packet): 1489 """ 1490 7.1.22 Read Remote Extended Features command 1491 """ 1492 name = "HCI_Read_Remote_Supported_Features" 1493 fields_desc = [LEShortField("connection_handle", None), 1494 ByteField("page_number", None), ] 1495 1496 1497class HCI_Cmd_IO_Capability_Request_Reply(Packet): 1498 """ 1499 7.1.29 IO Capability Request Reply command 1500 """ 1501 name = "HCI_Read_Remote_Supported_Features" 1502 fields_desc = [LEMACField("bd_addr", None), 1503 ByteEnumField("io_capability", None, {0x00: "DisplayOnly", 1504 0x01: "DisplayYesNo", 1505 0x02: "KeyboardOnly", 1506 0x03: "NoInputNoOutput", }), 1507 ByteEnumField("oob_data_present", None, {0x00: "Not Present", 1508 0x01: "P-192", 1509 0x02: "P-256", 1510 0x03: "P-192 + P-256", }), 1511 ByteEnumField("authentication_requirement", None, 1512 {0x00: "MITM Not Required", 1513 0x01: "MITM Required, No Bonding", 1514 0x02: "MITM Not Required + Dedicated Pairing", 1515 0x03: "MITM Required + Dedicated Pairing", 1516 0x04: "MITM Not Required, General Bonding", 1517 0x05: "MITM Required + General Bonding"}), ] 1518 1519 1520class HCI_Cmd_User_Confirmation_Request_Reply(Packet): 1521 """ 1522 7.1.30 User Confirmation Request Reply command 1523 """ 1524 name = "HCI_User_Confirmation_Request_Reply" 1525 fields_desc = [LEMACField("bd_addr", None), ] 1526 1527 1528class HCI_Cmd_User_Confirmation_Request_Negative_Reply(Packet): 1529 """ 1530 7.1.31 User Confirmation Request Negative Reply command 1531 """ 1532 name = "HCI_User_Confirmation_Request_Negative_Reply" 1533 fields_desc = [LEMACField("bd_addr", None), ] 1534 1535 1536class HCI_Cmd_User_Passkey_Request_Reply(Packet): 1537 """ 1538 7.1.32 User Passkey Request Reply command 1539 """ 1540 name = "HCI_User_Passkey_Request_Reply" 1541 fields_desc = [LEMACField("bd_addr", None), 1542 LEIntField("numeric_value", None), ] 1543 1544 1545class HCI_Cmd_User_Passkey_Request_Negative_Reply(Packet): 1546 """ 1547 7.1.33 User Passkey Request Negative Reply command 1548 """ 1549 name = "HCI_User_Passkey_Request_Negative_Reply" 1550 fields_desc = [LEMACField("bd_addr", None), ] 1551 1552 1553class HCI_Cmd_Remote_OOB_Data_Request_Reply(Packet): 1554 """ 1555 7.1.34 Remote OOB Data Request Reply command 1556 """ 1557 name = "HCI_Remote_OOB_Data_Request_Reply" 1558 fields_desc = [LEMACField("bd_addr", None), 1559 NBytesField("C", b"\x00" * 16, sz=16), 1560 NBytesField("R", b"\x00" * 16, sz=16), ] 1561 1562 1563class HCI_Cmd_Remote_OOB_Data_Request_Negative_Reply(Packet): 1564 """ 1565 7.1.35 Remote OOB Data Request Negative Reply command 1566 """ 1567 name = "HCI_Remote_OOB_Data_Request_Negative_Reply" 1568 fields_desc = [LEMACField("bd_addr", None), ] 1569 1570 1571# 7.2 Link Policy commands, the OGF is defined as 0x02 1572 1573class HCI_Cmd_Hold_Mode(Packet): 1574 name = "HCI_Hold_Mode" 1575 fields_desc = [LEShortField("connection_handle", 0), 1576 LEShortField("hold_mode_max_interval", 0x0002), 1577 LEShortField("hold_mode_min_interval", 0x0002), ] 1578 1579 1580# 7.3 CONTROLLER & BASEBAND COMMANDS, the OGF is defined as 0x03 1581 1582class HCI_Cmd_Set_Event_Mask(Packet): 1583 """ 1584 7.3.1 Set Event Mask command 1585 """ 1586 name = "HCI_Set_Event_Mask" 1587 fields_desc = [StrFixedLenField("mask", b"\xff\xff\xfb\xff\x07\xf8\xbf\x3d", 8)] # noqa: E501 1588 1589 1590class HCI_Cmd_Reset(Packet): 1591 """ 1592 7.3.2 Reset command 1593 """ 1594 name = "HCI_Reset" 1595 1596 1597class HCI_Cmd_Set_Event_Filter(Packet): 1598 """ 1599 7.3.3 Set Event Filter command 1600 """ 1601 name = "HCI_Set_Event_Filter" 1602 fields_desc = [ByteEnumField("type", 0, {0: "clear"}), ] 1603 1604 1605class HCI_Cmd_Write_Local_Name(Packet): 1606 """ 1607 7.3.11 Write Local Name command 1608 """ 1609 name = "HCI_Write_Local_Name" 1610 fields_desc = [StrFixedLenField('name', '', length=248)] 1611 1612 1613class HCI_Cmd_Read_Local_Name(Packet): 1614 """ 1615 7.3.12 Read Local Name command 1616 """ 1617 name = "HCI_Read_Local_Name" 1618 1619 1620class HCI_Cmd_Write_Connect_Accept_Timeout(Packet): 1621 name = "HCI_Write_Connection_Accept_Timeout" 1622 fields_desc = [LEShortField("timeout", 32000)] # 32000 slots is 20000 msec 1623 1624 1625class HCI_Cmd_Write_Extended_Inquiry_Response(Packet): 1626 name = "HCI_Write_Extended_Inquiry_Response" 1627 fields_desc = [ByteField("fec_required", 0), 1628 HCI_Extended_Inquiry_Response] 1629 1630 1631class HCI_Cmd_Read_LE_Host_Support(Packet): 1632 name = "HCI_Read_LE_Host_Support" 1633 1634 1635class HCI_Cmd_Write_LE_Host_Support(Packet): 1636 name = "HCI_Write_LE_Host_Support" 1637 fields_desc = [ByteField("supported", 1), 1638 ByteField("unused", 1), ] 1639 1640 1641# 7.4 INFORMATIONAL PARAMETERS, the OGF is defined as 0x04 1642 1643class HCI_Cmd_Read_Local_Version_Information(Packet): 1644 """ 1645 7.4.1 Read Local Version Information command 1646 """ 1647 name = "HCI_Read_Local_Version_Information" 1648 1649 1650class HCI_Cmd_Read_Local_Extended_Features(Packet): 1651 """ 1652 7.4.4 Read Local Extended Features command 1653 """ 1654 name = "HCI_Read_Local_Extended_Features" 1655 fields_desc = [ByteField("page_number", 0)] 1656 1657 1658class HCI_Cmd_Read_BD_Addr(Packet): 1659 """ 1660 7.4.6 Read BD_ADDR command 1661 """ 1662 name = "HCI_Read_BD_ADDR" 1663 1664 1665# 7.5 STATUS PARAMETERS, the OGF is defined as 0x05 1666 1667class HCI_Cmd_Read_Link_Quality(Packet): 1668 name = "HCI_Read_Link_Quality" 1669 fields_desc = [LEShortField("handle", 0)] 1670 1671 1672class HCI_Cmd_Read_RSSI(Packet): 1673 name = "HCI_Read_RSSI" 1674 fields_desc = [LEShortField("handle", 0)] 1675 1676 1677# 7.6 TESTING COMMANDS, the OGF is defined as 0x06 1678 1679class HCI_Cmd_Read_Loopback_Mode(Packet): 1680 name = "HCI_Read_Loopback_Mode" 1681 1682 1683class HCI_Cmd_Write_Loopback_Mode(Packet): 1684 name = "HCI_Write_Loopback_Mode" 1685 fields_desc = [ByteEnumField("loopback_mode", 0, 1686 {0: "no loopback", 1687 1: "enable local loopback", 1688 2: "enable remote loopback"})] 1689 1690 1691# 7.8 LE CONTROLLER COMMANDS, the OGF code is defined as 0x08 1692 1693class HCI_Cmd_LE_Read_Buffer_Size_V1(Packet): 1694 name = "HCI_LE_Read_Buffer_Size [v1]" 1695 1696 1697class HCI_Cmd_LE_Read_Buffer_Size_V2(Packet): 1698 name = "HCI_LE_Read_Buffer_Size [v2]" 1699 1700 1701class HCI_Cmd_LE_Read_Local_Supported_Features(Packet): 1702 name = "HCI_LE_Read_Local_Supported_Features" 1703 1704 1705class HCI_Cmd_LE_Set_Random_Address(Packet): 1706 name = "HCI_LE_Set_Random_Address" 1707 fields_desc = [LEMACField("address", None)] 1708 1709 1710class HCI_Cmd_LE_Set_Advertising_Parameters(Packet): 1711 name = "HCI_LE_Set_Advertising_Parameters" 1712 fields_desc = [LEShortField("interval_min", 0x0800), 1713 LEShortField("interval_max", 0x0800), 1714 ByteEnumField("adv_type", 0, {0: "ADV_IND", 1: "ADV_DIRECT_IND", 2: "ADV_SCAN_IND", 3: "ADV_NONCONN_IND", 4: "ADV_DIRECT_IND_LOW"}), # noqa: E501 1715 ByteEnumField("oatype", 0, {0: "public", 1: "random"}), 1716 ByteEnumField("datype", 0, {0: "public", 1: "random"}), 1717 LEMACField("daddr", None), 1718 ByteField("channel_map", 7), 1719 ByteEnumField("filter_policy", 0, {0: "all:all", 1: "connect:all scan:whitelist", 2: "connect:whitelist scan:all", 3: "all:whitelist"}), ] # noqa: E501 1720 1721 1722class HCI_Cmd_LE_Set_Advertising_Data(Packet): 1723 name = "HCI_LE_Set_Advertising_Data" 1724 fields_desc = [FieldLenField("len", None, length_of="data", fmt="B"), 1725 PadField( 1726 PacketListField("data", [], EIR_Hdr, 1727 length_from=lambda pkt: pkt.len), 1728 align=31, padwith=b"\0"), ] 1729 1730 1731class HCI_Cmd_LE_Set_Scan_Response_Data(Packet): 1732 name = "HCI_LE_Set_Scan_Response_Data" 1733 fields_desc = [FieldLenField("len", None, length_of="data", fmt="B"), 1734 StrLenField("data", "", length_from=lambda pkt: pkt.len), ] 1735 1736 1737class HCI_Cmd_LE_Set_Advertise_Enable(Packet): 1738 name = "HCI_LE_Set_Advertising_Enable" 1739 fields_desc = [ByteField("enable", 0)] 1740 1741 1742class HCI_Cmd_LE_Set_Scan_Parameters(Packet): 1743 name = "HCI_LE_Set_Scan_Parameters" 1744 fields_desc = [ByteEnumField("type", 0, {0: "passive", 1: "active"}), 1745 XLEShortField("interval", 16), 1746 XLEShortField("window", 16), 1747 ByteEnumField("atype", 0, {0: "public", 1748 1: "random", 1749 2: "rpa (pub)", 1750 3: "rpa (random)"}), 1751 ByteEnumField("policy", 0, {0: "all", 1: "whitelist"})] 1752 1753 1754class HCI_Cmd_LE_Set_Scan_Enable(Packet): 1755 name = "HCI_LE_Set_Scan_Enable" 1756 fields_desc = [ByteField("enable", 1), 1757 ByteField("filter_dups", 1), ] 1758 1759 1760class HCI_Cmd_LE_Create_Connection(Packet): 1761 name = "HCI_LE_Create_Connection" 1762 fields_desc = [LEShortField("interval", 96), 1763 LEShortField("window", 48), 1764 ByteEnumField("filter", 0, {0: "address"}), 1765 ByteEnumField("patype", 0, {0: "public", 1: "random"}), 1766 LEMACField("paddr", None), 1767 ByteEnumField("atype", 0, {0: "public", 1: "random"}), 1768 LEShortField("min_interval", 40), 1769 LEShortField("max_interval", 56), 1770 LEShortField("latency", 0), 1771 LEShortField("timeout", 42), 1772 LEShortField("min_ce", 0), 1773 LEShortField("max_ce", 0), ] 1774 1775 1776class HCI_Cmd_LE_Create_Connection_Cancel(Packet): 1777 name = "HCI_LE_Create_Connection_Cancel" 1778 1779 1780class HCI_Cmd_LE_Read_Filter_Accept_List_Size(Packet): 1781 name = "HCI_LE_Read_Filter_Accept_List_Size" 1782 1783 1784class HCI_Cmd_LE_Clear_Filter_Accept_List(Packet): 1785 name = "HCI_LE_Clear_Filter_Accept_List" 1786 1787 1788class HCI_Cmd_LE_Add_Device_To_Filter_Accept_List(Packet): 1789 name = "HCI_LE_Add_Device_To_Filter_Accept_List" 1790 fields_desc = [ByteEnumField("address_type", 0, {0: "public", 1791 1: "random", 1792 0xff: "anonymous"}), 1793 LEMACField("address", None)] 1794 1795 1796class HCI_Cmd_LE_Remove_Device_From_Filter_Accept_List(HCI_Cmd_LE_Add_Device_To_Filter_Accept_List): # noqa: E501 1797 name = "HCI_LE_Remove_Device_From_Filter_Accept_List" 1798 1799 1800class HCI_Cmd_LE_Connection_Update(Packet): 1801 name = "HCI_LE_Connection_Update" 1802 fields_desc = [XLEShortField("handle", 0), 1803 XLEShortField("min_interval", 0), 1804 XLEShortField("max_interval", 0), 1805 XLEShortField("latency", 0), 1806 XLEShortField("timeout", 0), 1807 LEShortField("min_ce", 0), 1808 LEShortField("max_ce", 0xffff), ] 1809 1810 1811class HCI_Cmd_LE_Read_Remote_Features(Packet): 1812 name = "HCI_LE_Read_Remote_Features" 1813 fields_desc = [LEShortField("handle", 64)] 1814 1815 1816class HCI_Cmd_LE_Enable_Encryption(Packet): 1817 name = "HCI_LE_Enable_Encryption" 1818 fields_desc = [LEShortField("handle", 0), 1819 StrFixedLenField("rand", None, 8), 1820 XLEShortField("ediv", 0), 1821 StrFixedLenField("ltk", b'\x00' * 16, 16), ] 1822 1823 1824class HCI_Cmd_LE_Long_Term_Key_Request_Reply(Packet): 1825 name = "HCI_LE_Long_Term_Key_Request_Reply" 1826 fields_desc = [LEShortField("handle", 0), 1827 StrFixedLenField("ltk", b'\x00' * 16, 16), ] 1828 1829 1830class HCI_Cmd_LE_Long_Term_Key_Request_Negative_Reply(Packet): 1831 name = "HCI_LE_Long_Term_Key_Request _Negative_Reply" 1832 fields_desc = [LEShortField("handle", 0), ] 1833 1834 1835class HCI_Event_Hdr(Packet): 1836 name = "HCI Event header" 1837 fields_desc = [XByteField("code", 0), 1838 LenField("len", None, fmt="B"), ] 1839 1840 def answers(self, other): 1841 if HCI_Command_Hdr not in other: 1842 return False 1843 1844 # Delegate answers to event types 1845 return self.payload.answers(other) 1846 1847 1848class HCI_Event_Inquiry_Complete(Packet): 1849 """ 1850 7.7.1 Inquiry Complete event 1851 """ 1852 name = "HCI_Inquiry_Complete" 1853 fields_desc = [ 1854 ByteEnumField('status', 0, _bluetooth_error_codes) 1855 ] 1856 1857 1858class HCI_Event_Inquiry_Result(Packet): 1859 """ 1860 7.7.2 Inquiry Result event 1861 """ 1862 name = "HCI_Inquiry_Result" 1863 fields_desc = [ 1864 ByteField("num_response", 0x00), 1865 FieldListField("addr", None, LEMACField("addr", None), 1866 count_from=lambda p: p.num_response), 1867 FieldListField("page_scan_repetition_mode", None, 1868 ByteField("page_scan_repetition_mode", 0), 1869 count_from=lambda p: p.num_response), 1870 FieldListField("reserved", None, LEShortField("reserved", 0), 1871 count_from=lambda p: p.num_response), 1872 FieldListField("device_class", None, XLE3BytesField("device_class", 0), 1873 count_from=lambda p: p.num_response), 1874 FieldListField("clock_offset", None, LEShortField("clock_offset", 0), 1875 count_from=lambda p: p.num_response) 1876 ] 1877 1878 1879class HCI_Event_Connection_Complete(Packet): 1880 """ 1881 7.7.3 Connection Complete event 1882 """ 1883 name = "HCI_Connection_Complete" 1884 fields_desc = [ByteEnumField('status', 0, _bluetooth_error_codes), 1885 LEShortField("handle", 0x0100), 1886 LEMACField("bd_addr", None), 1887 ByteEnumField("link_type", 0, {0: "SCO connection", 1888 1: "ACL connection", }), 1889 ByteEnumField("encryption_enabled", 0, 1890 {0: "link level encryption disabled", 1891 1: "link level encryption enabled", }), ] 1892 1893 1894class HCI_Event_Disconnection_Complete(Packet): 1895 """ 1896 7.7.5 Disconnection Complete event 1897 """ 1898 name = "HCI_Disconnection_Complete" 1899 fields_desc = [ByteEnumField("status", 0, _bluetooth_error_codes), 1900 LEShortField("handle", 0), 1901 XByteField("reason", 0), ] 1902 1903 1904class HCI_Event_Remote_Name_Request_Complete(Packet): 1905 """ 1906 7.7.7 Remote Name Request Complete event 1907 """ 1908 name = "HCI_Remote_Name_Request_Complete" 1909 fields_desc = [ByteEnumField("status", 0, _bluetooth_error_codes), 1910 LEMACField("bd_addr", None), 1911 StrFixedLenField("remote_name", b"\x00", 248), ] 1912 1913 1914class HCI_Event_Encryption_Change(Packet): 1915 """ 1916 7.7.8 Encryption Change event 1917 """ 1918 name = "HCI_Encryption_Change" 1919 fields_desc = [ByteEnumField("status", 0, {0: "change has occurred"}), 1920 LEShortField("handle", 0), 1921 ByteEnumField("enabled", 0, {0: "OFF", 1: "ON (LE)", 2: "ON (BR/EDR)"}), ] # noqa: E501 1922 1923 1924class HCI_Event_Read_Remote_Supported_Features_Complete(Packet): 1925 """ 1926 7.7.11 Read Remote Supported Features Complete event 1927 """ 1928 name = "HCI_Read_Remote_Supported_Features_Complete" 1929 fields_desc = [ 1930 ByteEnumField('status', 0, _bluetooth_error_codes), 1931 LEShortField('handle', 0), 1932 FlagsField('lmp_features', 0, -64, _bluetooth_features) 1933 ] 1934 1935 1936class HCI_Event_Read_Remote_Version_Information_Complete(Packet): 1937 """ 1938 7.7.12 Read Remote Version Information Complete event 1939 """ 1940 name = "HCI_Read_Remote_Version_Information" 1941 fields_desc = [ 1942 ByteEnumField('status', 0, _bluetooth_error_codes), 1943 LEShortField('handle', 0), 1944 ByteField('version', 0x00), 1945 LEShortField('manufacturer_name', 0x0000), 1946 LEShortField('subversion', 0x0000) 1947 ] 1948 1949 1950class HCI_Event_Command_Complete(Packet): 1951 """ 1952 7.7.14 Command Complete event 1953 """ 1954 name = "HCI_Command_Complete" 1955 fields_desc = [ByteField("number", 0), 1956 XLEShortField("opcode", 0), 1957 ByteEnumField("status", 0, _bluetooth_error_codes)] 1958 1959 def answers(self, other): 1960 if HCI_Command_Hdr not in other: 1961 return False 1962 1963 return other[HCI_Command_Hdr].opcode == self.opcode 1964 1965 1966class HCI_Event_Command_Status(Packet): 1967 """ 1968 7.7.15 Command Status event 1969 """ 1970 name = "HCI_Command_Status" 1971 fields_desc = [ByteEnumField("status", 0, {0: "pending"}), 1972 ByteField("number", 0), 1973 XLEShortField("opcode", None), ] 1974 1975 def answers(self, other): 1976 if HCI_Command_Hdr not in other: 1977 return False 1978 1979 return other[HCI_Command_Hdr].opcode == self.opcode 1980 1981 1982class HCI_Event_Number_Of_Completed_Packets(Packet): 1983 """ 1984 7.7.19 Number Of Completed Packets event 1985 """ 1986 name = "HCI_Number_Of_Completed_Packets" 1987 fields_desc = [ByteField("num_handles", 0), 1988 FieldListField("connection_handle_list", None, 1989 LEShortField("connection_handle", 0), 1990 count_from=lambda p: p.num_handles), 1991 FieldListField("num_completed_packets_list", None, 1992 LEShortField("num_completed_packets", 0), 1993 count_from=lambda p: p.num_handles)] 1994 1995 1996class HCI_Event_Link_Key_Request(Packet): 1997 """ 1998 7.7.23 Link Key Request event 1999 """ 2000 name = 'HCI_Link_Key_Request' 2001 fields_desc = [ 2002 LEMACField('bd_addr', None) 2003 ] 2004 2005 2006class HCI_Event_Inquiry_Result_With_Rssi(Packet): 2007 """ 2008 7.7.33 Inquiry Result with RSSI event 2009 """ 2010 name = "HCI_Inquiry_Result_with_RSSI" 2011 fields_desc = [ 2012 ByteField("num_response", 0x00), 2013 FieldListField("bd_addr", None, LEMACField, 2014 count_from=lambda p: p.num_response), 2015 FieldListField("page_scan_repetition_mode", None, ByteField, 2016 count_from=lambda p: p.num_response), 2017 FieldListField("reserved", None, LEShortField, 2018 count_from=lambda p: p.num_response), 2019 FieldListField("device_class", None, XLE3BytesField, 2020 count_from=lambda p: p.num_response), 2021 FieldListField("clock_offset", None, LEShortField, 2022 count_from=lambda p: p.num_response), 2023 FieldListField("rssi", None, SignedByteField, 2024 count_from=lambda p: p.num_response) 2025 ] 2026 2027 2028class HCI_Event_Read_Remote_Extended_Features_Complete(Packet): 2029 """ 2030 7.7.34 Read Remote Extended Features Complete event 2031 """ 2032 name = "HCI_Read_Remote_Extended_Features_Complete" 2033 fields_desc = [ 2034 ByteEnumField('status', 0, _bluetooth_error_codes), 2035 LEShortField('handle', 0), 2036 ByteField('page', 0x00), 2037 ByteField('max_page', 0x00), 2038 XLELongField('extended_features', 0) 2039 ] 2040 2041 2042class HCI_Event_Extended_Inquiry_Result(Packet): 2043 """ 2044 7.7.38 Extended Inquiry Result event 2045 """ 2046 name = "HCI_Extended_Inquiry_Result" 2047 fields_desc = [ 2048 ByteField('num_response', 0x01), 2049 LEMACField('bd_addr', None), 2050 ByteField('page_scan_repetition_mode', 0x00), 2051 ByteField('reserved', 0x00), 2052 XLE3BytesField('device_class', 0x000000), 2053 LEShortField('clock_offset', 0x0000), 2054 SignedByteField('rssi', 0x00), 2055 HCI_Extended_Inquiry_Response, 2056 ] 2057 2058 2059class HCI_Event_IO_Capability_Response(Packet): 2060 """ 2061 7.7.41 IO Capability Response event 2062 """ 2063 name = "HCI_IO_Capability_Response" 2064 fields_desc = [ 2065 LEMACField('bd_addr', None), 2066 ByteField('io_capability', 0x00), 2067 ByteField('oob_data_present', 0x00), 2068 ByteField('authentication_requirements', 0x00) 2069 ] 2070 2071 2072class HCI_Event_LE_Meta(Packet): 2073 """ 2074 7.7.65 LE Meta event 2075 """ 2076 name = "HCI_LE_Meta" 2077 fields_desc = [ByteEnumField("event", 0, { 2078 1: "connection_complete", 2079 2: "advertising_report", 2080 3: "connection_update_complete", 2081 5: "long_term_key_request", 2082 }), ] 2083 2084 def answers(self, other): 2085 if not self.payload: 2086 return False 2087 2088 # Delegate answers to payload 2089 return self.payload.answers(other) 2090 2091 2092class HCI_Cmd_Complete_Read_Local_Name(Packet): 2093 """ 2094 7.3.12 Read Local Name command complete 2095 """ 2096 name = 'Read Local Name command complete' 2097 fields_desc = [StrFixedLenField('local_name', '', length=248)] 2098 2099 2100class HCI_Cmd_Complete_Read_Local_Version_Information(Packet): 2101 """ 2102 7.4.1 Read Local Version Information command complete 2103 """ 2104 name = 'Read Local Version Information' 2105 fields_desc = [ 2106 ByteField('hci_version', 0), 2107 LEShortField('hci_subversion', 0), 2108 ByteField('lmp_version', 0), 2109 LEShortField('company_identifier', 0), 2110 LEShortField('lmp_subversion', 0)] 2111 2112 2113class HCI_Cmd_Complete_Read_Local_Extended_Features(Packet): 2114 """ 2115 7.4.4 Read Local Extended Features command complete 2116 """ 2117 name = 'Read Local Extended Features command complete' 2118 fields_desc = [ 2119 ByteField('page', 0x00), 2120 ByteField('max_page', 0x00), 2121 XLELongField('extended_features', 0) 2122 ] 2123 2124 2125class HCI_Cmd_Complete_Read_BD_Addr(Packet): 2126 """ 2127 7.4.6 Read BD_ADDR command complete 2128 """ 2129 name = "Read BD Addr" 2130 fields_desc = [LEMACField("addr", None), ] 2131 2132 2133class HCI_Cmd_Complete_LE_Read_White_List_Size(Packet): 2134 name = "LE Read White List Size" 2135 fields_desc = [ByteField("status", 0), 2136 ByteField("size", 0), ] 2137 2138 2139class HCI_LE_Meta_Connection_Complete(Packet): 2140 name = "Connection Complete" 2141 fields_desc = [ByteEnumField("status", 0, {0: "success"}), 2142 LEShortField("handle", 0), 2143 ByteEnumField("role", 0, {0: "master"}), 2144 ByteEnumField("patype", 0, {0: "public", 1: "random"}), 2145 LEMACField("paddr", None), 2146 LEShortField("interval", 54), 2147 LEShortField("latency", 0), 2148 LEShortField("supervision", 42), 2149 XByteField("clock_latency", 5), ] 2150 2151 def answers(self, other): 2152 if HCI_Cmd_LE_Create_Connection not in other: 2153 return False 2154 2155 return (other[HCI_Cmd_LE_Create_Connection].patype == self.patype and 2156 other[HCI_Cmd_LE_Create_Connection].paddr == self.paddr) 2157 2158 2159class HCI_LE_Meta_Connection_Update_Complete(Packet): 2160 name = "Connection Update Complete" 2161 fields_desc = [ByteEnumField("status", 0, {0: "success"}), 2162 LEShortField("handle", 0), 2163 LEShortField("interval", 54), 2164 LEShortField("latency", 0), 2165 LEShortField("timeout", 42), ] 2166 2167 2168class HCI_LE_Meta_Advertising_Report(Packet): 2169 name = "Advertising Report" 2170 fields_desc = [ByteEnumField("type", 0, {0: "conn_und", 4: "scan_rsp"}), 2171 ByteEnumField("atype", 0, {0: "public", 1: "random"}), 2172 LEMACField("addr", None), 2173 FieldLenField("len", None, length_of="data", fmt="B"), 2174 PacketListField("data", [], EIR_Hdr, 2175 length_from=lambda pkt: pkt.len), 2176 SignedByteField("rssi", 0)] 2177 2178 def extract_padding(self, s): 2179 return '', s 2180 2181 2182class HCI_LE_Meta_Advertising_Reports(Packet): 2183 name = "Advertising Reports" 2184 fields_desc = [FieldLenField("len", None, count_of="reports", fmt="B"), 2185 PacketListField("reports", None, 2186 HCI_LE_Meta_Advertising_Report, 2187 count_from=lambda pkt: pkt.len)] 2188 2189 2190class HCI_LE_Meta_Long_Term_Key_Request(Packet): 2191 name = "Long Term Key Request" 2192 fields_desc = [LEShortField("handle", 0), 2193 StrFixedLenField("rand", None, 8), 2194 XLEShortField("ediv", 0), ] 2195 2196 2197bind_layers(HCI_PHDR_Hdr, HCI_Hdr) 2198 2199bind_layers(HCI_Hdr, HCI_Command_Hdr, type=1) 2200bind_layers(HCI_Hdr, HCI_ACL_Hdr, type=2) 2201bind_layers(HCI_Hdr, HCI_Event_Hdr, type=4) 2202bind_layers(HCI_Hdr, conf.raw_layer,) 2203 2204conf.l2types.register(DLT_BLUETOOTH_HCI_H4, HCI_Hdr) 2205conf.l2types.register(DLT_BLUETOOTH_HCI_H4_WITH_PHDR, HCI_PHDR_Hdr) 2206 2207 2208# 7.1 LINK CONTROL COMMANDS, the OGF is defined as 0x01 2209bind_layers(HCI_Command_Hdr, HCI_Cmd_Inquiry, ogf=0x01, ocf=0x0001) 2210bind_layers(HCI_Command_Hdr, HCI_Cmd_Inquiry_Cancel, ogf=0x01, ocf=0x0002) 2211bind_layers(HCI_Command_Hdr, HCI_Cmd_Periodic_Inquiry_Mode, ogf=0x01, ocf=0x0003) 2212bind_layers(HCI_Command_Hdr, HCI_Cmd_Exit_Peiodic_Inquiry_Mode, ogf=0x01, ocf=0x0004) 2213bind_layers(HCI_Command_Hdr, HCI_Cmd_Create_Connection, ogf=0x01, ocf=0x0005) 2214bind_layers(HCI_Command_Hdr, HCI_Cmd_Disconnect, ogf=0x01, ocf=0x0006) 2215bind_layers(HCI_Command_Hdr, HCI_Cmd_Create_Connection_Cancel, ogf=0x01, ocf=0x0008) 2216bind_layers(HCI_Command_Hdr, HCI_Cmd_Accept_Connection_Request, ogf=0x01, ocf=0x0009) 2217bind_layers(HCI_Command_Hdr, HCI_Cmd_Reject_Connection_Response, ogf=0x01, ocf=0x000a) 2218bind_layers(HCI_Command_Hdr, HCI_Cmd_Link_Key_Request_Reply, ogf=0x01, ocf=0x000b) 2219bind_layers(HCI_Command_Hdr, HCI_Cmd_Link_Key_Request_Negative_Reply, 2220 ogf=0x01, ocf=0x000c) 2221bind_layers(HCI_Command_Hdr, HCI_Cmd_PIN_Code_Request_Reply, ogf=0x01, ocf=0x000d) 2222bind_layers(HCI_Command_Hdr, HCI_Cmd_Change_Connection_Packet_Type, 2223 ogf=0x01, ocf=0x000f) 2224bind_layers(HCI_Command_Hdr, HCI_Cmd_Authentication_Requested, ogf=0x01, ocf=0x0011) 2225bind_layers(HCI_Command_Hdr, HCI_Cmd_Set_Connection_Encryption, ogf=0x01, ocf=0x0013) 2226bind_layers(HCI_Command_Hdr, HCI_Cmd_Change_Connection_Link_Key, ogf=0x01, ocf=0x0017) 2227bind_layers(HCI_Command_Hdr, HCI_Cmd_Remote_Name_Request, ogf=0x01, ocf=0x0019) 2228bind_layers(HCI_Command_Hdr, HCI_Cmd_Remote_Name_Request_Cancel, ogf=0x01, ocf=0x001a) 2229bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Remote_Supported_Features, 2230 ogf=0x01, ocf=0x001b) 2231bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Remote_Extended_Features, 2232 ogf=0x01, ocf=0x001c) 2233bind_layers(HCI_Command_Hdr, HCI_Cmd_IO_Capability_Request_Reply, ogf=0x01, ocf=0x002b) 2234bind_layers(HCI_Command_Hdr, HCI_Cmd_User_Confirmation_Request_Reply, 2235 ogf=0x01, ocf=0x002c) 2236bind_layers(HCI_Command_Hdr, HCI_Cmd_User_Confirmation_Request_Negative_Reply, 2237 ogf=0x01, ocf=0x002d) 2238bind_layers(HCI_Command_Hdr, HCI_Cmd_User_Passkey_Request_Reply, ogf=0x01, ocf=0x002e) 2239bind_layers(HCI_Command_Hdr, HCI_Cmd_User_Passkey_Request_Negative_Reply, 2240 ogf=0x01, ocf=0x002f) 2241bind_layers(HCI_Command_Hdr, HCI_Cmd_Remote_OOB_Data_Request_Reply, 2242 ogf=0x01, ocf=0x0030) 2243bind_layers(HCI_Command_Hdr, HCI_Cmd_Remote_OOB_Data_Request_Negative_Reply, 2244 ogf=0x01, ocf=0x0033) 2245 2246# 7.2 Link Policy commands, the OGF is defined as 0x02 2247bind_layers(HCI_Command_Hdr, HCI_Cmd_Hold_Mode, ogf=0x02, ocf=0x0001) 2248 2249# 7.3 CONTROLLER & BASEBAND COMMANDS, the OGF is defined as 0x03 2250bind_layers(HCI_Command_Hdr, HCI_Cmd_Set_Event_Mask, ogf=0x03, ocf=0x0001) 2251bind_layers(HCI_Command_Hdr, HCI_Cmd_Reset, ogf=0x03, ocf=0x0003) 2252bind_layers(HCI_Command_Hdr, HCI_Cmd_Set_Event_Filter, ogf=0x03, ocf=0x0005) 2253bind_layers(HCI_Command_Hdr, HCI_Cmd_Write_Local_Name, ogf=0x03, ocf=0x0013) 2254bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Local_Name, ogf=0x03, ocf=0x0014) 2255bind_layers(HCI_Command_Hdr, HCI_Cmd_Write_Connect_Accept_Timeout, ogf=0x03, ocf=0x0016) 2256bind_layers(HCI_Command_Hdr, HCI_Cmd_Write_Extended_Inquiry_Response, ogf=0x03, ocf=0x0052) # noqa: E501 2257bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_LE_Host_Support, ogf=0x03, ocf=0x006c) 2258bind_layers(HCI_Command_Hdr, HCI_Cmd_Write_LE_Host_Support, ogf=0x03, ocf=0x006d) 2259 2260# 7.4 INFORMATIONAL PARAMETERS, the OGF is defined as 0x04 2261bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Local_Version_Information, ogf=0x04, ocf=0x0001) # noqa: E501 2262bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Local_Extended_Features, ogf=0x04, ocf=0x0004) 2263bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_BD_Addr, ogf=0x04, ocf=0x0009) 2264 2265# 7.5 STATUS PARAMETERS, the OGF is defined as 0x05 2266bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Link_Quality, ogf=0x05, ocf=0x0003) 2267bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_RSSI, ogf=0x05, ocf=0x0005) 2268 2269# 7.6 TESTING COMMANDS, the OGF is defined as 0x06 2270bind_layers(HCI_Command_Hdr, HCI_Cmd_Read_Loopback_Mode, ogf=0x06, ocf=0x0001) 2271bind_layers(HCI_Command_Hdr, HCI_Cmd_Write_Loopback_Mode, ogf=0x06, ocf=0x0002) 2272 2273# 7.8 LE CONTROLLER COMMANDS, the OGF code is defined as 0x08 2274bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Read_Buffer_Size_V1, ogf=0x08, ocf=0x0002) 2275bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Read_Buffer_Size_V2, ogf=0x08, ocf=0x0060) 2276bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Read_Local_Supported_Features, 2277 ogf=0x08, ocf=0x0003) 2278bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Random_Address, ogf=0x08, ocf=0x0005) 2279bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Advertising_Parameters, ogf=0x08, ocf=0x0006) # noqa: E501 2280bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Advertising_Data, ogf=0x08, ocf=0x0008) 2281bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Scan_Response_Data, ogf=0x08, ocf=0x0009) 2282bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Advertise_Enable, ogf=0x08, ocf=0x000a) 2283bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Scan_Parameters, ogf=0x08, ocf=0x000b) 2284bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Set_Scan_Enable, ogf=0x08, ocf=0x000c) 2285bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Create_Connection, ogf=0x08, ocf=0x000d) 2286bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Create_Connection_Cancel, ogf=0x08, ocf=0x000e) # noqa: E501 2287bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Read_Filter_Accept_List_Size, 2288 ogf=0x08, ocf=0x000f) 2289bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Clear_Filter_Accept_List, ogf=0x08, ocf=0x0010) 2290bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Add_Device_To_Filter_Accept_List, ogf=0x08, ocf=0x0011) # noqa: E501 2291bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Remove_Device_From_Filter_Accept_List, ogf=0x08, ocf=0x0012) # noqa: E501 2292bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Connection_Update, ogf=0x08, ocf=0x0013) 2293bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Read_Remote_Features, ogf=0x08, ocf=0x0016) # noqa: E501 2294bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Enable_Encryption, ogf=0x08, ocf=0x0019) # noqa: E501 2295bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Long_Term_Key_Request_Reply, ogf=0x08, ocf=0x001a) # noqa: E501 2296bind_layers(HCI_Command_Hdr, HCI_Cmd_LE_Long_Term_Key_Request_Negative_Reply, ogf=0x08, ocf=0x001b) # noqa: E501 2297 2298# 7.7 EVENTS 2299bind_layers(HCI_Event_Hdr, HCI_Event_Inquiry_Complete, code=0x01) 2300bind_layers(HCI_Event_Hdr, HCI_Event_Inquiry_Result, code=0x02) 2301bind_layers(HCI_Event_Hdr, HCI_Event_Connection_Complete, code=0x03) 2302bind_layers(HCI_Event_Hdr, HCI_Event_Disconnection_Complete, code=0x05) 2303bind_layers(HCI_Event_Hdr, HCI_Event_Remote_Name_Request_Complete, code=0x07) 2304bind_layers(HCI_Event_Hdr, HCI_Event_Encryption_Change, code=0x08) 2305bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Supported_Features_Complete, code=0x0b) 2306bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Version_Information_Complete, code=0x0c) # noqa: E501 2307bind_layers(HCI_Event_Hdr, HCI_Event_Command_Complete, code=0x0e) 2308bind_layers(HCI_Event_Hdr, HCI_Event_Command_Status, code=0x0f) 2309bind_layers(HCI_Event_Hdr, HCI_Event_Number_Of_Completed_Packets, code=0x13) 2310bind_layers(HCI_Event_Hdr, HCI_Event_Link_Key_Request, code=0x17) 2311bind_layers(HCI_Event_Hdr, HCI_Event_Inquiry_Result_With_Rssi, code=0x22) 2312bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Extended_Features_Complete, code=0x23) 2313bind_layers(HCI_Event_Hdr, HCI_Event_Extended_Inquiry_Result, code=0x2f) 2314bind_layers(HCI_Event_Hdr, HCI_Event_IO_Capability_Response, code=0x32) 2315bind_layers(HCI_Event_Hdr, HCI_Event_LE_Meta, code=0x3e) 2316 2317bind_layers(HCI_Event_Command_Complete, HCI_Cmd_Complete_Read_Local_Name, opcode=0x0c14) # noqa: E501 2318bind_layers(HCI_Event_Command_Complete, HCI_Cmd_Complete_Read_Local_Version_Information, opcode=0x1001) # noqa: E501 2319bind_layers(HCI_Event_Command_Complete, HCI_Cmd_Complete_Read_Local_Extended_Features, opcode=0x1004) # noqa: E501 2320bind_layers(HCI_Event_Command_Complete, HCI_Cmd_Complete_Read_BD_Addr, opcode=0x1009) # noqa: E501 2321bind_layers(HCI_Event_Command_Complete, HCI_Cmd_Complete_LE_Read_White_List_Size, opcode=0x200f) # noqa: E501 2322 2323bind_layers(HCI_Event_LE_Meta, HCI_LE_Meta_Connection_Complete, event=1) 2324bind_layers(HCI_Event_LE_Meta, HCI_LE_Meta_Advertising_Reports, event=2) 2325bind_layers(HCI_Event_LE_Meta, HCI_LE_Meta_Connection_Update_Complete, event=3) 2326bind_layers(HCI_Event_LE_Meta, HCI_LE_Meta_Long_Term_Key_Request, event=5) 2327 2328bind_layers(EIR_Hdr, EIR_Flags, type=0x01) 2329bind_layers(EIR_Hdr, EIR_IncompleteList16BitServiceUUIDs, type=0x02) 2330bind_layers(EIR_Hdr, EIR_CompleteList16BitServiceUUIDs, type=0x03) 2331bind_layers(EIR_Hdr, EIR_IncompleteList32BitServiceUUIDs, type=0x04) 2332bind_layers(EIR_Hdr, EIR_CompleteList32BitServiceUUIDs, type=0x05) 2333bind_layers(EIR_Hdr, EIR_IncompleteList128BitServiceUUIDs, type=0x06) 2334bind_layers(EIR_Hdr, EIR_CompleteList128BitServiceUUIDs, type=0x07) 2335bind_layers(EIR_Hdr, EIR_ShortenedLocalName, type=0x08) 2336bind_layers(EIR_Hdr, EIR_CompleteLocalName, type=0x09) 2337bind_layers(EIR_Hdr, EIR_Device_ID, type=0x10) 2338bind_layers(EIR_Hdr, EIR_TX_Power_Level, type=0x0a) 2339bind_layers(EIR_Hdr, EIR_ClassOfDevice, type=0x0d) 2340bind_layers(EIR_Hdr, EIR_SecureSimplePairingHashC192, type=0x0e) 2341bind_layers(EIR_Hdr, EIR_SecureSimplePairingRandomizerR192, type=0x0f) 2342bind_layers(EIR_Hdr, EIR_SecurityManagerOOBFlags, type=0x11) 2343bind_layers(EIR_Hdr, EIR_PeripheralConnectionIntervalRange, type=0x12) 2344bind_layers(EIR_Hdr, EIR_ServiceData16BitUUID, type=0x16) 2345bind_layers(EIR_Hdr, EIR_ServiceData32BitUUID, type=0x20) 2346bind_layers(EIR_Hdr, EIR_ServiceData128BitUUID, type=0x21) 2347bind_layers(EIR_Hdr, EIR_Manufacturer_Specific_Data, type=0xff) 2348bind_layers(EIR_Hdr, EIR_Raw) 2349 2350bind_layers(HCI_ACL_Hdr, L2CAP_Hdr,) 2351bind_layers(L2CAP_Hdr, L2CAP_CmdHdr, cid=1) 2352bind_layers(L2CAP_Hdr, L2CAP_CmdHdr, cid=5) # LE L2CAP Signaling Channel 2353bind_layers(L2CAP_CmdHdr, L2CAP_CmdRej, code=1) 2354bind_layers(L2CAP_CmdHdr, L2CAP_ConnReq, code=2) 2355bind_layers(L2CAP_CmdHdr, L2CAP_ConnResp, code=3) 2356bind_layers(L2CAP_CmdHdr, L2CAP_ConfReq, code=4) 2357bind_layers(L2CAP_CmdHdr, L2CAP_ConfResp, code=5) 2358bind_layers(L2CAP_CmdHdr, L2CAP_DisconnReq, code=6) 2359bind_layers(L2CAP_CmdHdr, L2CAP_DisconnResp, code=7) 2360bind_layers(L2CAP_CmdHdr, L2CAP_EchoReq, code=8) 2361bind_layers(L2CAP_CmdHdr, L2CAP_EchoResp, code=9) 2362bind_layers(L2CAP_CmdHdr, L2CAP_InfoReq, code=10) 2363bind_layers(L2CAP_CmdHdr, L2CAP_InfoResp, code=11) 2364bind_layers(L2CAP_CmdHdr, L2CAP_Create_Channel_Request, code=12) 2365bind_layers(L2CAP_CmdHdr, L2CAP_Create_Channel_Response, code=13) 2366bind_layers(L2CAP_CmdHdr, L2CAP_Move_Channel_Request, code=14) 2367bind_layers(L2CAP_CmdHdr, L2CAP_Move_Channel_Response, code=15) 2368bind_layers(L2CAP_CmdHdr, L2CAP_Move_Channel_Confirmation_Request, code=16) 2369bind_layers(L2CAP_CmdHdr, L2CAP_Move_Channel_Confirmation_Response, code=17) 2370bind_layers(L2CAP_CmdHdr, L2CAP_Connection_Parameter_Update_Request, code=18) 2371bind_layers(L2CAP_CmdHdr, L2CAP_Connection_Parameter_Update_Response, code=19) 2372bind_layers(L2CAP_CmdHdr, L2CAP_LE_Credit_Based_Connection_Request, code=20) 2373bind_layers(L2CAP_CmdHdr, L2CAP_LE_Credit_Based_Connection_Response, code=21) 2374bind_layers(L2CAP_CmdHdr, L2CAP_Flow_Control_Credit_Ind, code=22) 2375bind_layers(L2CAP_CmdHdr, L2CAP_Credit_Based_Connection_Request, code=23) 2376bind_layers(L2CAP_CmdHdr, L2CAP_Credit_Based_Connection_Response, code=24) 2377bind_layers(L2CAP_CmdHdr, L2CAP_Credit_Based_Reconfigure_Request, code=25) 2378bind_layers(L2CAP_CmdHdr, L2CAP_Credit_Based_Reconfigure_Response, code=26) 2379bind_layers(L2CAP_Hdr, ATT_Hdr, cid=4) 2380bind_layers(ATT_Hdr, ATT_Error_Response, opcode=0x1) 2381bind_layers(ATT_Hdr, ATT_Exchange_MTU_Request, opcode=0x2) 2382bind_layers(ATT_Hdr, ATT_Exchange_MTU_Response, opcode=0x3) 2383bind_layers(ATT_Hdr, ATT_Find_Information_Request, opcode=0x4) 2384bind_layers(ATT_Hdr, ATT_Find_Information_Response, opcode=0x5) 2385bind_layers(ATT_Hdr, ATT_Find_By_Type_Value_Request, opcode=0x6) 2386bind_layers(ATT_Hdr, ATT_Find_By_Type_Value_Response, opcode=0x7) 2387bind_layers(ATT_Hdr, ATT_Read_By_Type_Request_128bit, opcode=0x8) 2388bind_layers(ATT_Hdr, ATT_Read_By_Type_Request, opcode=0x8) 2389bind_layers(ATT_Hdr, ATT_Read_By_Type_Response, opcode=0x9) 2390bind_layers(ATT_Hdr, ATT_Read_Request, opcode=0xa) 2391bind_layers(ATT_Hdr, ATT_Read_Response, opcode=0xb) 2392bind_layers(ATT_Hdr, ATT_Read_Blob_Request, opcode=0xc) 2393bind_layers(ATT_Hdr, ATT_Read_Blob_Response, opcode=0xd) 2394bind_layers(ATT_Hdr, ATT_Read_Multiple_Request, opcode=0xe) 2395bind_layers(ATT_Hdr, ATT_Read_Multiple_Response, opcode=0xf) 2396bind_layers(ATT_Hdr, ATT_Read_By_Group_Type_Request, opcode=0x10) 2397bind_layers(ATT_Hdr, ATT_Read_By_Group_Type_Response, opcode=0x11) 2398bind_layers(ATT_Hdr, ATT_Write_Request, opcode=0x12) 2399bind_layers(ATT_Hdr, ATT_Write_Response, opcode=0x13) 2400bind_layers(ATT_Hdr, ATT_Prepare_Write_Request, opcode=0x16) 2401bind_layers(ATT_Hdr, ATT_Prepare_Write_Response, opcode=0x17) 2402bind_layers(ATT_Hdr, ATT_Execute_Write_Request, opcode=0x18) 2403bind_layers(ATT_Hdr, ATT_Execute_Write_Response, opcode=0x19) 2404bind_layers(ATT_Hdr, ATT_Write_Command, opcode=0x52) 2405bind_layers(ATT_Hdr, ATT_Handle_Value_Notification, opcode=0x1b) 2406bind_layers(ATT_Hdr, ATT_Handle_Value_Indication, opcode=0x1d) 2407bind_layers(L2CAP_Hdr, SM_Hdr, cid=6) 2408bind_layers(SM_Hdr, SM_Pairing_Request, sm_command=1) 2409bind_layers(SM_Hdr, SM_Pairing_Response, sm_command=2) 2410bind_layers(SM_Hdr, SM_Confirm, sm_command=3) 2411bind_layers(SM_Hdr, SM_Random, sm_command=4) 2412bind_layers(SM_Hdr, SM_Failed, sm_command=5) 2413bind_layers(SM_Hdr, SM_Encryption_Information, sm_command=6) 2414bind_layers(SM_Hdr, SM_Master_Identification, sm_command=7) 2415bind_layers(SM_Hdr, SM_Identity_Information, sm_command=8) 2416bind_layers(SM_Hdr, SM_Identity_Address_Information, sm_command=9) 2417bind_layers(SM_Hdr, SM_Signing_Information, sm_command=0x0a) 2418bind_layers(SM_Hdr, SM_Public_Key, sm_command=0x0c) 2419bind_layers(SM_Hdr, SM_DHKey_Check, sm_command=0x0d) 2420 2421 2422############### 2423# HCI Monitor # 2424############### 2425 2426 2427# https://elixir.bootlin.com/linux/v6.4.2/source/include/net/bluetooth/hci_mon.h#L27 2428class HCI_Mon_Hdr(Packet): 2429 name = 'Bluetooth Linux Monitor Transport Header' 2430 fields_desc = [ 2431 LEShortEnumField('opcode', None, { 2432 0: "New index", 2433 1: "Delete index", 2434 2: "Command pkt", 2435 3: "Event pkt", 2436 4: "ACL TX pkt", 2437 5: "ACL RX pkt", 2438 6: "SCO TX pkt", 2439 7: "SCO RX pkt", 2440 8: "Open index", 2441 9: "Close index", 2442 10: "Index info", 2443 11: "Vendor diag", 2444 12: "System note", 2445 13: "User logging", 2446 14: "Ctrl open", 2447 15: "Ctrl close", 2448 16: "Ctrl command", 2449 17: "Ctrl event", 2450 18: "ISO TX pkt", 2451 19: "ISO RX pkt", 2452 }), 2453 LEShortField('adapter_id', None), 2454 LEShortField('len', None) 2455 ] 2456 2457 2458# https://www.tcpdump.org/linktypes/LINKTYPE_BLUETOOTH_LINUX_MONITOR.html 2459class HCI_Mon_Pcap_Hdr(HCI_Mon_Hdr): 2460 name = 'Bluetooth Linux Monitor Transport Pcap Header' 2461 fields_desc = [ 2462 ShortField('adapter_id', None), 2463 ShortField('opcode', None) 2464 ] 2465 2466 2467class HCI_Mon_New_Index(Packet): 2468 name = 'Bluetooth Linux Monitor Transport New Index Packet' 2469 fields_desc = [ 2470 ByteEnumField('bus', 0, { 2471 0x00: "BR/EDR", 2472 0x01: "AMP" 2473 }), 2474 ByteEnumField('type', 0, { 2475 0x00: "Virtual", 2476 0x01: "USB", 2477 0x02: "PC Card", 2478 0x03: "UART", 2479 0x04: "RS232", 2480 0x05: "PCI", 2481 0x06: "SDIO" 2482 }), 2483 LEMACField('addr', None), 2484 StrFixedLenField('devname', None, 8) 2485 ] 2486 2487 2488class HCI_Mon_Index_Info(Packet): 2489 name = 'Bluetooth Linux Monitor Transport Index Info Packet' 2490 fields_desc = [ 2491 LEMACField('addr', None), 2492 XLEShortField('manufacturer', None) 2493 ] 2494 2495 2496class HCI_Mon_System_Note(Packet): 2497 name = 'Bluetooth Linux Monitor Transport System Note Packet' 2498 fields_desc = [ 2499 StrNullField('note', None) 2500 ] 2501 2502 2503# https://elixir.bootlin.com/linux/v6.4.2/source/include/net/bluetooth/hci_mon.h#L34 2504bind_layers(HCI_Mon_Hdr, HCI_Mon_New_Index, opcode=0) 2505bind_layers(HCI_Mon_Hdr, HCI_Command_Hdr, opcode=2) 2506bind_layers(HCI_Mon_Hdr, HCI_Event_Hdr, opcode=3) 2507bind_layers(HCI_Mon_Hdr, HCI_Mon_Index_Info, opcode=10) 2508bind_layers(HCI_Mon_Hdr, HCI_Mon_System_Note, opcode=12) 2509 2510conf.l2types.register(DLT_BLUETOOTH_LINUX_MONITOR, HCI_Mon_Pcap_Hdr) 2511 2512 2513########### 2514# Helpers # 2515########### 2516 2517class LowEnergyBeaconHelper: 2518 """ 2519 Helpers for building packets for Bluetooth Low Energy Beacons. 2520 2521 Implementers provide a :meth:`build_eir` implementation. 2522 2523 This is designed to be used as a mix-in -- see 2524 ``scapy.contrib.eddystone`` and ``scapy.contrib.ibeacon`` for examples. 2525 """ 2526 2527 # Basic flags that should be used by most beacons. 2528 base_eir = [EIR_Hdr() / EIR_Flags(flags=[ 2529 "general_disc_mode", "br_edr_not_supported"]), ] 2530 2531 def build_eir(self): 2532 """ 2533 Builds a list of EIR messages to wrap this frame. 2534 2535 Users of this helper must implement this method. 2536 2537 :return: List of HCI_Hdr with payloads that describe this beacon type 2538 :rtype: list[scapy.bluetooth.HCI_Hdr] 2539 """ 2540 raise NotImplementedError("build_eir") 2541 2542 def build_advertising_report(self): 2543 """ 2544 Builds a HCI_LE_Meta_Advertising_Report containing this frame. 2545 2546 :rtype: scapy.bluetooth.HCI_LE_Meta_Advertising_Report 2547 """ 2548 2549 return HCI_LE_Meta_Advertising_Report( 2550 type=0, # Undirected 2551 atype=1, # Random address 2552 data=self.build_eir() 2553 ) 2554 2555 def build_set_advertising_data(self): 2556 """Builds a HCI_Cmd_LE_Set_Advertising_Data containing this frame. 2557 2558 This includes the :class:`HCI_Hdr` and :class:`HCI_Command_Hdr` layers. 2559 2560 :rtype: scapy.bluetooth.HCI_Hdr 2561 """ 2562 2563 return HCI_Hdr() / HCI_Command_Hdr() / HCI_Cmd_LE_Set_Advertising_Data( 2564 data=self.build_eir() 2565 ) 2566 2567 2568########### 2569# Sockets # 2570########### 2571 2572class BluetoothSocketError(BaseException): 2573 pass 2574 2575 2576class BluetoothCommandError(BaseException): 2577 pass 2578 2579 2580class BluetoothL2CAPSocket(SuperSocket): 2581 desc = "read/write packets on a connected L2CAP socket" 2582 2583 def __init__(self, bt_address): 2584 if WINDOWS: 2585 warning("Not available on Windows") 2586 return 2587 s = socket.socket(socket.AF_BLUETOOTH, socket.SOCK_RAW, 2588 socket.BTPROTO_L2CAP) 2589 s.connect((bt_address, 0)) 2590 self.ins = self.outs = s 2591 2592 def recv(self, x=MTU): 2593 return L2CAP_CmdHdr(self.ins.recv(x)) 2594 2595 2596class BluetoothRFCommSocket(BluetoothL2CAPSocket): 2597 """read/write packets on a connected RFCOMM socket""" 2598 2599 def __init__(self, bt_address, port=0): 2600 s = socket.socket(socket.AF_BLUETOOTH, socket.SOCK_RAW, 2601 socket.BTPROTO_RFCOMM) 2602 s.connect((bt_address, port)) 2603 self.ins = self.outs = s 2604 2605 2606class BluetoothHCISocket(SuperSocket): 2607 desc = "read/write on a BlueTooth HCI socket" 2608 2609 def __init__(self, iface=0x10000, type=None): 2610 if WINDOWS: 2611 warning("Not available on Windows") 2612 return 2613 s = socket.socket(socket.AF_BLUETOOTH, socket.SOCK_RAW, socket.BTPROTO_HCI) # noqa: E501 2614 s.setsockopt(socket.SOL_HCI, socket.HCI_DATA_DIR, 1) 2615 s.setsockopt(socket.SOL_HCI, socket.HCI_TIME_STAMP, 1) 2616 s.setsockopt(socket.SOL_HCI, socket.HCI_FILTER, struct.pack("IIIh2x", 0xffffffff, 0xffffffff, 0xffffffff, 0)) # type mask, event mask, event mask, opcode # noqa: E501 2617 s.bind((iface,)) 2618 self.ins = self.outs = s 2619# s.connect((peer,0)) 2620 2621 def recv(self, x=MTU): 2622 return HCI_Hdr(self.ins.recv(x)) 2623 2624 2625class sockaddr_hci(ctypes.Structure): 2626 _fields_ = [ 2627 ("sin_family", ctypes.c_ushort), 2628 ("hci_dev", ctypes.c_ushort), 2629 ("hci_channel", ctypes.c_ushort), 2630 ] 2631 2632 2633class _BluetoothLibcSocket(SuperSocket): 2634 def __init__(self, socket_domain, socket_type, socket_protocol, sock_address): 2635 # type: (int, int, int, sockaddr_hci) -> None 2636 if WINDOWS: 2637 warning("Not available on Windows") 2638 return 2639 # Python socket and bind implementations do not allow us to pass down 2640 # the correct parameters. We must call libc functions directly via 2641 # ctypes. 2642 sockaddr_hcip = ctypes.POINTER(sockaddr_hci) 2643 from ctypes.util import find_library 2644 libc = ctypes.cdll.LoadLibrary(find_library("c")) 2645 2646 socket_c = libc.socket 2647 socket_c.argtypes = (ctypes.c_int, ctypes.c_int, ctypes.c_int) 2648 socket_c.restype = ctypes.c_int 2649 2650 bind = libc.bind 2651 bind.argtypes = (ctypes.c_int, 2652 ctypes.POINTER(sockaddr_hci), 2653 ctypes.c_int) 2654 bind.restype = ctypes.c_int 2655 2656 # Socket 2657 s = socket_c(socket_domain, socket_type, socket_protocol) 2658 if s < 0: 2659 raise BluetoothSocketError( 2660 f"Unable to open socket({socket_domain}, {socket_type}, " 2661 f"{socket_protocol})") 2662 2663 # Bind 2664 r = bind(s, sockaddr_hcip(sock_address), sizeof(sock_address)) 2665 if r != 0: 2666 raise BluetoothSocketError("Unable to bind") 2667 2668 self.hci_fd = s 2669 self.ins = self.outs = socket.fromfd( 2670 s, socket_domain, socket_type, socket_protocol) 2671 2672 def readable(self, timeout=0): 2673 (ins, _, _) = select.select([self.ins], [], [], timeout) 2674 return len(ins) > 0 2675 2676 def flush(self): 2677 while self.readable(): 2678 self.recv() 2679 2680 def close(self): 2681 if self.closed: 2682 return 2683 2684 # Properly close socket so we can free the device 2685 from ctypes.util import find_library 2686 libc = ctypes.cdll.LoadLibrary(find_library("c")) 2687 2688 close = libc.close 2689 close.restype = ctypes.c_int 2690 self.closed = True 2691 if hasattr(self, "outs"): 2692 if not hasattr(self, "ins") or self.ins != self.outs: 2693 if self.outs and (WINDOWS or self.outs.fileno() != -1): 2694 close(self.outs.fileno()) 2695 if hasattr(self, "ins"): 2696 if self.ins and (WINDOWS or self.ins.fileno() != -1): 2697 close(self.ins.fileno()) 2698 if hasattr(self, "hci_fd"): 2699 close(self.hci_fd) 2700 2701 2702class BluetoothUserSocket(_BluetoothLibcSocket): 2703 desc = "read/write H4 over a Bluetooth user channel" 2704 2705 def __init__(self, adapter_index=0): 2706 sa = sockaddr_hci() 2707 sa.sin_family = socket.AF_BLUETOOTH 2708 sa.hci_dev = adapter_index 2709 sa.hci_channel = HCI_CHANNEL_USER 2710 super().__init__( 2711 socket_domain=socket.AF_BLUETOOTH, 2712 socket_type=socket.SOCK_RAW, 2713 socket_protocol=socket.BTPROTO_HCI, 2714 sock_address=sa) 2715 2716 def send_command(self, cmd): 2717 opcode = cmd.opcode 2718 self.send(cmd) 2719 while True: 2720 r = self.recv() 2721 if r.type == 0x04 and r.code == 0xe and r.opcode == opcode: 2722 if r.status != 0: 2723 raise BluetoothCommandError("Command %x failed with %x" % (opcode, r.status)) # noqa: E501 2724 return r 2725 2726 def recv(self, x=MTU): 2727 return HCI_Hdr(self.ins.recv(x)) 2728 2729 2730class BluetoothMonitorSocket(_BluetoothLibcSocket): 2731 desc = "Read/write over a Bluetooth monitor channel" 2732 2733 def __init__(self): 2734 sa = sockaddr_hci() 2735 sa.sin_family = socket.AF_BLUETOOTH 2736 sa.hci_dev = HCI_DEV_NONE 2737 sa.hci_channel = HCI_CHANNEL_MONITOR 2738 super().__init__( 2739 socket_domain=socket.AF_BLUETOOTH, 2740 socket_type=socket.SOCK_RAW, 2741 socket_protocol=socket.BTPROTO_HCI, 2742 sock_address=sa) 2743 2744 def recv(self, x=MTU): 2745 return HCI_Mon_Hdr(self.ins.recv(x)) 2746 2747 2748conf.BTsocket = BluetoothRFCommSocket 2749 2750# Bluetooth 2751 2752 2753@conf.commands.register 2754def srbt(bt_address, pkts, inter=0.1, *args, **kargs): 2755 """send and receive using a bluetooth socket""" 2756 if "port" in kargs: 2757 s = conf.BTsocket(bt_address=bt_address, port=kargs.pop("port")) 2758 else: 2759 s = conf.BTsocket(bt_address=bt_address) 2760 a, b = sndrcv(s, pkts, inter=inter, *args, **kargs) 2761 s.close() 2762 return a, b 2763 2764 2765@conf.commands.register 2766def srbt1(bt_address, pkts, *args, **kargs): 2767 """send and receive 1 packet using a bluetooth socket""" 2768 a, b = srbt(bt_address, pkts, *args, **kargs) 2769 if len(a) > 0: 2770 return a[0][1] 2771