Summary
BRAVIA Professional Displays "Simple IP control" protocol for the Sony KDA87 Series. Sony's proprietary SSIP runs over TCP port 20060 using fixed 24-byte messages (2-byte header *S, 1-byte type, 4-byte Four-CC command, 16-byte parameters, 1-byte LF footer). No authentication is required. The protocol supports power, input, volume, mute, picture mute, scene setting, IR-passthrough, and basic network discovery (broadcast address, MAC address) commands.
Transport
protocols:
- tcp
addressing:
port: 20060
auth:
type: none # inferred: no auth procedure in source
Traits
- powerable # inferred from setPowerStatus / togglePowerStatus
- routable # inferred from setInput / getInput
- queryable # inferred from getPowerStatus / getAudioVolume / etc.
- levelable # inferred from setAudioVolume
Actions
- id: set_power_status
label: Set Power Status
kind: action
command: "*SCPOWR000000000000000{state}\n"
params:
- name: state
type: string
enum: [off, on]
description: 16th parameter byte (last) - "0" = Standby (Off), "1" = Active (On). Remaining 15 parameter bytes are "0". Full 24-byte message: `*SCPOWR` + 15×`0` + `0` or `1` + `\n`.
- id: get_power_status
label: Get Power Status
kind: query
command: "*SEPOWR################\n"
params: []
- id: toggle_power_status
label: Toggle Power Status
kind: action
command: "*SCTPOW################\n"
params: []
- id: set_audio_volume
label: Set Audio Volume
kind: action
command: "*SCVOLU{volume}\n"
params:
- name: volume
type: integer
description: Volume as decimal, right-padded with "0" to 16 chars (e.g. `0000000000000029` for value 29). Source notes "Set the volume value in the decimal digit pad on the left with 0". Maximum/minimum not stated in source.
- id: get_audio_volume
label: Get Audio Volume
kind: query
command: "*SEVOLU################\n"
params: []
- id: set_audio_mute
label: Set Audio Mute
kind: action
command: "*SCAMUT000000000000000{mute}\n"
params:
- name: mute
type: string
enum: [off, on]
description: 16th parameter byte - "0" = Unmute, "1" = Mute. Remaining 15 parameter bytes are "0".
- id: get_audio_mute
label: Get Audio Mute
kind: query
command: "*SEAMUT################\n"
params: []
- id: set_input
label: Set Input
kind: action
command: "*SCINPT0000000000{kind}000{port}\n"
params:
- name: kind
type: integer
enum: [1, 3, 4, 5]
description: 8th parameter byte (byte[14] of full message): 1=HDMI, 3=Composite, 4=Component, 5=Screen Mirroring.
- name: port
type: integer
description: 4-digit decimal, right-padded with "0" to 4 chars (e.g. "0001" for input 1). Range stated as 1-9999.
- id: get_input
label: Get Input
kind: query
command: "*SEINPT################\n"
params: []
- id: set_picture_mute
label: Set Picture Mute
kind: action
command: "*SCPMUT000000000000000{state}\n"
params:
- name: state
type: string
enum: [off, on]
description: 16th parameter byte - "0" = Disables picture mute, "1" = Turns the screen black (picture mute). Remaining 15 parameter bytes are "0".
- id: get_picture_mute
label: Get Picture Mute
kind: query
command: "*SEPMUT################\n"
params: []
- id: toggle_picture_mute
label: Toggle Picture Mute
kind: action
command: "*SCTPMU################\n"
params: []
- id: set_scene_setting
label: Set Scene Setting
kind: action
command: "*SCSCEN{scene}\n"
params:
- name: scene
type: string
enum: [auto, auto24pSync, general]
description: Scene name, right-padded with `#` to 16 chars (e.g. `auto24pSync#####`). Case-sensitive.
- id: get_scene_setting
label: Get Scene Setting
kind: query
command: "*SESCEN################\n"
params: []
- id: get_broadcast_address
label: Get Broadcast Address
kind: query
command: "*SEBADReth0###########\n"
params: []
# UNRESOLVED: source states parameter is the interface name (e.g. "eth0"), padded to 16 chars with "#". The set of valid interface names is not enumerated in source. Example payload is hard-coded to `eth0` above; replace with target interface.
- id: get_mac_address
label: Get MAC Address
kind: query
command: "*SEMADReth0###########\n"
params: []
# UNRESOLVED: same as get_broadcast_address - interface name not enumerated in source.
- id: set_ircc_code
label: Set IR Remote Control Code
kind: action
command: "*SCIRCC00000000000000{code}\n"
params:
- name: code
type: integer
enum: [5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 30, 31, 32, 33, 34, 35, 38, 50, 61, 62, 76, 77, 78, 79, 80, 81, 82, 84, 86, 87, 98, 99, 101, 104, 105, 108, 110, 121, 124, 125, 126, 127, 129, 130]
description: IR code value, 2-digit decimal at the last two parameter positions (byte[21..22]). Remaining 14 parameter bytes are "0". Codes from the IR Commands table. Common ones: Display=5, Home=6, Options=7, Return=8, Up=9, Down=10, Right=11, Left=12, Confirm=13, Red=14, Green=15, Yellow=16, Blue=17, Num1-9=18-26, Num0=27, Volume Up=30, Volume Down=31, Mute=32, Channel Up/Down=33/34, Subtitle=35, DOT=38, Picture Off=50, Wide=61, Jump=62, Sync Menu=76, Forward=77, Play=78, Rewind=79, Prev=80, Stop=81, Next=82, Pause=84, Flash Plus/Minus=86/87, TV Power=98, Audio=99, Input=101, Sleep=104, Sleep Timer=105, Video 2=108, Picture Mode=110, Demo Surround=121, HDMI 1-4=124-127, Action Menu=129, Help=130.
Feedbacks
- id: power_state
type: enum
values: [off, on]
# Answer to getPowerStatus: byte[22] = "0" → Standby (Off); "1" → Active (On). "F…" → error.
- id: audio_volume
type: integer
# Answer to getAudioVolume: 16 parameter bytes - decimal volume right-padded with "0".
- id: audio_mute_state
type: enum
values: [unmuted, muted]
# Answer to getAudioMute: byte[22] = "0" → Not Muted; "1" → Muted. "F…" → error.
- id: current_input
type: object
# Answer to getInput: byte[14] = input kind (1=HDMI, 3=Composite, 4=Component, 5=Screen Mirroring); bytes[19..22] = 4-digit port number, right-padded with "0".
- id: picture_mute_state
type: enum
values: [disabled, enabled]
# Answer to getPictureMute: byte[22] = "0" → Disabled; "1" → Enabled. "F…" → error.
- id: scene_setting
type: string
enum: [auto, auto24pSync, general]
# Answer to getSceneSetting: 16-byte parameter string, right-padded with "#". "N…" → not available for current input. "F…" → error.
- id: broadcast_address
type: string
# Answer to getBroadcastAddress: 16-byte IPv4 address string, right-padded with "#" (e.g. "192.168.0.14####").
- id: mac_address
type: string
# Answer to getMacAddress: 12-hex MAC, right-padded with "#" to 16 chars.
- id: command_result
type: enum
values: [success, not_found, error, not_available]
# Common Answer prefix: 16×"0" = success; 16×"F" = error; 16×"N" = not found / not available for current input.
Variables
# No settable parameters beyond those exposed via Actions (volume, mute, input, picture mute, scene, power).
Events
- id: fire_power_change
command: "*SNPOWR000000000000000{state}\n"
description: Sent by monitor on power change. byte[22] = "0" → powering off, "1" → powering on.
params:
- name: state
type: string
enum: [off, on]
- id: fire_input_change
command: "*SNINPT0000000000{kind}000{port}\n"
description: Sent by monitor on input change. byte[14] = input kind (1=HDMI, 3=Composite, 4=Component, 5=Screen Mirroring); bytes[19..22] = 4-digit port, right-padded with "0". A `0000000000000000` payload is sent for generic input change events.
params:
- name: kind
type: integer
enum: [0, 1, 3, 4, 5]
- name: port
type: integer
- id: fire_volume_change
command: "*SNVOLU{volume}\n"
description: Sent by monitor on volume change. 16-byte decimal volume, right-padded with "0".
params:
- name: volume
type: integer
- id: fire_mute_change
command: "*SNAMUT000000000000000{state}\n"
description: Sent by monitor on mute state change. byte[22] = "0" → unmuting, "1" → muting.
params:
- name: state
type: string
enum: [unmuted, muted]
- id: fire_picture_mute_change
command: "*SNPMUT000000000000000{state}\n"
description: Sent by monitor on picture mute change. byte[22] = "0" → picture mute enabled, "1" → picture mute disabled. (Note: inverted relative to the set/get command polarity.)
params:
- name: state
type: string
enum: [enabled, disabled]
Macros
# UNRESOLVED: source does not describe multi-step sequences; remove or populate when source provides them.
Safety
confirmation_required_for: []
interlocks: []
# UNRESOLVED: source contains no explicit safety warnings, interlocks, or power-on sequencing requirements. EU models have RED-DA conditional command availability but the source does not characterize it as a safety interlock.
Notes
- Frame format: 24 bytes total. Header
*S(0x2A 0x53), then byte[2] = type (C/E/A/N), bytes[3..6] = Four-CC command, bytes[7..22] = 16-byte parameter block, byte[23] = LF (0x0A). - Padding: parameter block is always exactly 16 bytes. Numeric values are right-padded with
0; string values are right-padded with#; unused fields are filled with#for enquiry/control-without-parameters and0for success answers orFfor error answers. - Message type semantics: Control (
C) Client→Monitor with no parameters used for toggle functions; Enquiry (E) Client→Monitor with no parameters; Answer (A) Monitor→Client (16×0= success, 16×F= error, 16×N= not found / not available for current input); Notify (N) Monitor→Client unsolicited events. - Netcat example from source:
netcat [IP address] 20060, then send*SCPOWR0000000000000000\nto power off. The monitor responds with*SAPOWR0000000000000000 *SNPOWR0000000000000000(accept + notify). - EU RED-DA: source flags that EU-area models have 3 RED-DA compliance variants with different available command sets; this spec reflects the commands listed for the base protocol and does not enumerate per-variant deltas.
- IR command codes are passed via
setIrccCodeand the enum above covers the full IR Commands table from the source.
Provenance
source_domains:
- pro-bravia.sony.net
- aca.im
source_urls:
- https://pro-bravia.sony.net/remote-display-control/simple-ip-control/
- https://pro-bravia.sony.net/remote-display-control/rest-api/structure/
- https://pro-bravia.sony.net/remote-display-control/ip-control-comparison/
- "https://aca.im/driver_docs/Sony/sony%20bravia%20simple%20ip%20control.pdf"
- https://pro-bravia.sony.net/
retrieved_at: 2026-06-10T00:17:33.288Z
last_checked_at: 2026-06-10T07:33:49.275Z
Verification Summary
verdict: verified
checked_at: 2026-06-10T07:33:49.275Z
matched_actions: 17
action_count: 17
confidence: medium
summary: "All 17 spec actions match their wire tokens exactly in the source command table. Transport (TCP 20060, no auth) verified. Bidirectional coverage complete. (6 unresolved item(s) noted in Known Gaps.)"
Known Gaps
- "EU RED-DA variant spec availability is conditional and not enumerated; source states \"3 types of specifications based on RED-DA compliance. Settings and available commands differ for each specification\" but the variant matrix is on a separate page not provided."
- "source states parameter is the interface name (e.g. \"eth0\"), padded to 16 chars with \"#\". The set of valid interface names is not enumerated in source. Example payload is hard-coded to `eth0` above; replace with target interface."
- "same as get_broadcast_address - interface name not enumerated in source."
- "source does not describe multi-step sequences; remove or populate when source provides them."
- "source contains no explicit safety warnings, interlocks, or power-on sequencing requirements. EU models have RED-DA conditional command availability but the source does not characterize it as a safety interlock."
- "volume min/max bounds not stated in source. Interface names for getBroadcastAddress / getMacAddress are not enumerated; `eth0` shown as example. Firmware version compatibility not stated."
From the AI4AV catalog (https://ai4av.net) · ODbL-1.0