Protocol Overview
Soulseek uses a hybrid peer-to-peer architecture:- Central server - Manages user authentication, searches, and peer discovery
- Peer connections - Direct connections between users for file transfers
- Distributed network - For distributing search queries efficiently
The Soulseek server and client are proprietary software. The protocol has been documented through years of reverse engineering by the community.
Key Components
Server Messages
Clients communicate with the Soulseek server over TCP connections. Server messages handle:- User login and authentication
- Room management (joining, leaving, chat messages)
- Search distribution
- Peer address resolution
- User statistics and status updates
- Privilege management
- Code 1: Login
- Code 13: Say in Chat Room
- Code 14: Join Room
- Code 26: File Search
- Code 93: Embedded Message (distributed search)
Peer Messages
Peer-to-peer connections are established between users for:- File transfers (uploads and downloads)
- Share browsing
- Search result delivery
- Queue management
- Direct messaging
P- Peer to Peer (general communication)F- File Transfer (actual file data)D- Distributed Network (search distribution)
Distributed Network
Soulseek uses a distributed search network to reduce server load:1
Search initiated
User sends search query to server or distributed parent.
2
Distribution
Query propagates through the distributed network tree structure.
3
Results returned
Users with matching files send results directly to the searcher.
- Branch roots receive searches directly from the server
- Parents distribute searches to children
- Children search their shares and relay to their children
Your position in the distributed network depends on your upload speed. Faster connections become parents or branch roots.
Message Format
All Soulseek messages follow a consistent binary format:Server Messages
Data Types
The protocol uses little-endian encoding for all multi-byte integers:- uint8 - 8-bit unsigned integer (1 byte)
- uint16 - 16-bit unsigned integer (2 bytes, little-endian)
- uint32 - 32-bit unsigned integer (4 bytes, little-endian)
- uint64 - 64-bit unsigned integer (8 bytes, little-endian)
- bool - 1 byte (0 or 1)
- string - uint32 length + UTF-8 byte string
- bytes - uint32 length + raw byte array
Example: Login Message
A login message (server code 1) contains:Protocol Features
File Attributes
File search results include metadata attributes:- 0 - Bitrate (kbps)
- 1 - Duration (seconds)
- 2 - VBR flag (0 or 1)
- 4 - Sample Rate (Hz)
- 5 - Bit Depth (bits)
User Status Codes
0- Offline1- Away2- Online
Transfer States
File transfers can be in various states with rejection reasons: Active states:- Queued
- Transferring
- Complete
Banned- User is bannedCancelled- Transfer cancelled by userFile not shared.- File no longer availableToo many files- Upload limit reachedToo many megabytes- Bandwidth limit reachedQueued- Added to queue (not immediate)
Connection Process
Establishing a peer connection involves multiple steps:1
Request peer address
Client sends
GetPeerAddress message to server with target username.2
Receive peer info
Server responds with peer’s IP address and port.
3
Attempt direct connection
Client attempts to connect directly to peer.
4
Fallback to indirect
If direct connection fails, client sends
ConnectToPeer message.
Server relays the connection request, and peer connects back.5
Pierce firewall
Connection includes a
PierceFireWall message with a unique token.6
Peer initialization
After connection, peers exchange
PeerInit messages.Obfuscation
Some clients (like SoulseekQt) support message obfuscation:- Type 0 - No obfuscation (default)
- Type 1 - Rotated/obfuscated connection
Protocol Versions
Nicotine+ identifies itself with:- Version:
160 - Minor version:
1
- SoulseekQt:
157+ (various minor versions) - Soulseek NS:
143-157 - Museek+:
157
Security Considerations
Best practices:- Use a VPN - Hide your real IP address
- Unique password - Don’t reuse passwords from other services
- Bind to VPN - Use
--bindipto ensure traffic routes through VPN - Monitor shares - Only share files you’re comfortable being public
Implementation in Nicotine+
Nicotine+ implements the protocol in Python:pynicotine/slskmessages.py- Message definitions and parsingpynicotine/core.py- Core network handlingpynicotine/shares.py- File sharing and indexingpynicotine/transfers.py- Upload/download management
Detailed Protocol Documentation
For complete technical details about every message type, data structure, and protocol flow, see the comprehensive protocol documentation:SLSKPROTOCOL.md
Complete Soulseek protocol documentation with all message codes, data formats, and examples.Last updated: February 28, 2026
- All server message codes (1-160, 1001, 1003)
- Peer initialization messages
- Peer-to-peer message codes
- File transfer messages
- Distributed network messages
- Data packing formats
- Constants and enumerations
- Obsolete/deprecated messages
Alternative Implementations
Several Soulseek implementations exist:- Nicotine+ - Python (GTK or headless)
- SoulseekQt - C++ (official client)
- Soulseek NS - C++ (legacy official client)
- slskd - C# (web-based daemon)
- Museek+ - C++ (defunct)
- SoulSeeX - macOS client
Soulfind Server
For running your own Soulseek server:Soulfind
Open-source Soulseek server implementation. While not identical to the official server, it handles the protocol well and can be modified.
Protocol Extensions
If you find protocol inconsistencies or errors, report them to the Nicotine+ team.Learning More
To understand the protocol in depth:- Read the full documentation -
SLSKPROTOCOL.md - Study the source - Review
slskmessages.pyin Nicotine+ - Monitor traffic - Use Wireshark with the Soulseek dissector
- Test with plugins - Write plugins that interact with protocol events
Message Examples
Here’s how a file search works:1
Client sends FileSearch (code 26)
2
Server distributes to network
Server sends EmbeddedMessage (code 93) to branch roots, who distribute to children.
3
Peers send results
Peers with matches establish a connection and send FileSearchResult messages.
4
Client receives results
Results appear in the search tab, sorted by various criteria.
Contributing
If you discover protocol details or inconsistencies:- Test your findings with multiple clients
- Document the behavior with examples
- Submit an issue or pull request to the Nicotine+ repository
- Update
SLSKPROTOCOL.mdwith new information
Next Steps
- Explore Plugins to interact with protocol events
- Review CLI options for network binding
- Read the full SLSKPROTOCOL.md documentation