mirror of
https://github.com/librespot-org/librespot.git
synced 2024-12-18 17:11:53 +00:00
spirc: Don’t hardcode stuff
This commit is contained in:
parent
45491925de
commit
df11960946
4 changed files with 118 additions and 115 deletions
|
@ -13,11 +13,11 @@ message ClientResponseEncrypted {
|
|||
|
||||
message LoginCredentials {
|
||||
optional string username = 0xa;
|
||||
required Type typ = 0x14;
|
||||
required AuthenticationType typ = 0x14;
|
||||
optional bytes auth_data = 0x1e;
|
||||
}
|
||||
|
||||
enum Type {
|
||||
enum AuthenticationType {
|
||||
AUTHENTICATION_USER_PASS = 0x0;
|
||||
AUTHENTICATION_STORED_SPOTIFY_CREDENTIALS = 0x1;
|
||||
AUTHENTICATION_STORED_FACEBOOK_CREDENTIALS = 0x2;
|
||||
|
@ -134,21 +134,31 @@ message ClientInfoFacebook {
|
|||
optional string machine_id = 0x1;
|
||||
}
|
||||
|
||||
message AuthSuccess {
|
||||
required string username = 0x0a;
|
||||
required uint32 data1 = 0x14;
|
||||
required uint32 data2 = 0x19;
|
||||
required uint32 data3 = 0x1e;
|
||||
required bytes data4 = 0x28;
|
||||
required bytes data5 = 0x32;
|
||||
message APWelcome {
|
||||
required string canonical_username = 0xa;
|
||||
required AccountType account_type_logged_in = 0x14;
|
||||
required AccountType credentials_type_logged_in = 0x19;
|
||||
required AuthenticationType reusable_auth_credentials_type = 0x1e;
|
||||
required bytes reusable_auth_credentials = 0x28;
|
||||
optional bytes lfs_secret = 0x32;
|
||||
optional AccountInfo account_info = 0x3c;
|
||||
optional AccountInfoFacebook fb = 0x46;
|
||||
}
|
||||
|
||||
message AuthFailure {
|
||||
required uint32 code = 0x0a;
|
||||
required Data1 data1 = 0x32;
|
||||
|
||||
message Data1 {
|
||||
required string data0 = 0x01;
|
||||
}
|
||||
enum AccountType {
|
||||
Spotify = 0x0;
|
||||
Facebook = 0x1;
|
||||
}
|
||||
|
||||
message AccountInfo {
|
||||
optional AccountInfoSpotify spotify = 0x1;
|
||||
optional AccountInfoFacebook facebook = 0x2;
|
||||
}
|
||||
|
||||
message AccountInfoSpotify {
|
||||
}
|
||||
|
||||
message AccountInfoFacebook {
|
||||
optional string access_token = 0x1;
|
||||
optional string machine_id = 0x2;
|
||||
}
|
||||
|
|
|
@ -1,21 +1,21 @@
|
|||
// size=80
|
||||
|
||||
message ClientHello {
|
||||
required BuildInfo build_info = 0xa; // idx=0 offset=c
|
||||
repeated Fingerprint fingerprints_supported = 0x14; // idx=ffff offset=10
|
||||
repeated Cryptosuite cryptosuites_supported = 0x1e; // idx=ffff offset=2c
|
||||
repeated Powscheme powschemes_supported = 0x28; // idx=ffff offset=48
|
||||
required LoginCryptoHelloUnion login_crypto_hello = 0x32; // idx=1 offset=64
|
||||
required bytes client_nonce = 0x3c; // idx=2 offset=68 size=f
|
||||
optional bytes padding = 0x46; // idx=3 offset=78
|
||||
optional FeatureSet feature_set = 0x50; // idx=4 offset=7c
|
||||
required BuildInfo build_info = 0xa;
|
||||
repeated Fingerprint fingerprints_supported = 0x14;
|
||||
repeated Cryptosuite cryptosuites_supported = 0x1e;
|
||||
repeated Powscheme powschemes_supported = 0x28;
|
||||
required LoginCryptoHelloUnion login_crypto_hello = 0x32;
|
||||
required bytes client_nonce = 0x3c;
|
||||
optional bytes padding = 0x46;
|
||||
optional FeatureSet feature_set = 0x50;
|
||||
}
|
||||
|
||||
// size=38
|
||||
|
||||
message BuildInfo {
|
||||
required Product product = 0xa; // idx=0 offset=c
|
||||
repeated ProductFlags product_flags = 0x14; // idx=ffff offset=10
|
||||
required Platform platform = 0x1e; // idx=1 offset=2c
|
||||
required uint64 version = 0x28; // idx=2 offset=30 extra=246558
|
||||
required Product product = 0xa;
|
||||
repeated ProductFlags product_flags = 0x14;
|
||||
required Platform platform = 0x1e;
|
||||
required uint64 version = 0x28;
|
||||
}
|
||||
|
||||
enum Product {
|
||||
|
@ -72,108 +72,101 @@ enum Powscheme {
|
|||
POW_HASH_CASH = 0x0;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message LoginCryptoHelloUnion {
|
||||
optional LoginCryptoDiffieHellmanHello diffie_hellman = 0xa; // idx=0 offset=c
|
||||
optional LoginCryptoDiffieHellmanHello diffie_hellman = 0xa;
|
||||
}
|
||||
|
||||
// size=70
|
||||
|
||||
message LoginCryptoDiffieHellmanHello {
|
||||
required bytes gc = 0xa; // idx=0 offset=c size=5f
|
||||
required uint32 server_keys_known = 0x14; // idx=1 offset=6c
|
||||
required bytes gc = 0xa;
|
||||
required uint32 server_keys_known = 0x14;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message FeatureSet {
|
||||
optional bool autoupdate2 = 0x1; // idx=0 offset=c
|
||||
optional bool current_location = 0x2; // idx=1 offset=d
|
||||
optional bool autoupdate2 = 0x1;
|
||||
optional bool current_location = 0x2;
|
||||
}
|
||||
|
||||
|
||||
// size=18
|
||||
message APResponseMessage {
|
||||
optional APChallenge challenge = 0xa; // idx=0 offset=c
|
||||
optional UpgradeRequiredMessage upgrade = 0x14; // idx=1 offset=10
|
||||
optional APLoginFailed login_failed = 0x1e; // idx=2 offset=14
|
||||
optional APChallenge challenge = 0xa;
|
||||
optional UpgradeRequiredMessage upgrade = 0x14;
|
||||
optional APLoginFailed login_failed = 0x1e;
|
||||
}
|
||||
|
||||
// size=30
|
||||
message APChallenge {
|
||||
required LoginCryptoChallengeUnion login_crypto_challenge = 0xa; // idx=0 offset=c
|
||||
required FingerprintChallengeUnion fingerprint_challenge = 0x14; // idx=1 offset=10
|
||||
required PoWChallengeUnion pow_challenge = 0x1e; // idx=2 offset=14
|
||||
required CryptoChallengeUnion crypto_challenge = 0x28; // idx=3 offset=18
|
||||
required bytes server_nonce = 0x32; // idx=4 offset=1c size=f
|
||||
optional bytes padding = 0x3c; // idx=5 offset=2c
|
||||
required LoginCryptoChallengeUnion login_crypto_challenge = 0xa;
|
||||
required FingerprintChallengeUnion fingerprint_challenge = 0x14;
|
||||
required PoWChallengeUnion pow_challenge = 0x1e;
|
||||
required CryptoChallengeUnion crypto_challenge = 0x28;
|
||||
required bytes server_nonce = 0x32;
|
||||
optional bytes padding = 0x3c;
|
||||
}
|
||||
|
||||
// size=10
|
||||
message LoginCryptoChallengeUnion {
|
||||
optional LoginCryptoDiffieHellmanChallenge diffie_hellman = 0xa; // idx=0 offset=c
|
||||
optional LoginCryptoDiffieHellmanChallenge diffie_hellman = 0xa;
|
||||
}
|
||||
|
||||
// size=170
|
||||
message LoginCryptoDiffieHellmanChallenge {
|
||||
required bytes gs = 0xa; // idx=0 offset=c size=5f
|
||||
required int32 server_signature_key = 0x14; // idx=1 offset=6c type=int8
|
||||
required bytes gs_signature = 0x1e; // idx=2 offset=6d size=ff
|
||||
required bytes gs = 0xa;
|
||||
required int32 server_signature_key = 0x14;
|
||||
required bytes gs_signature = 0x1e;
|
||||
}
|
||||
|
||||
// size=14
|
||||
message FingerprintChallengeUnion {
|
||||
optional FingerprintGrainChallenge grain = 0xa; // idx=0 offset=c
|
||||
optional FingerprintHmacRipemdChallenge hmac_ripemd = 0x14; // idx=1 offset=10
|
||||
optional FingerprintGrainChallenge grain = 0xa;
|
||||
optional FingerprintHmacRipemdChallenge hmac_ripemd = 0x14;
|
||||
}
|
||||
|
||||
// size=1c
|
||||
|
||||
message FingerprintGrainChallenge {
|
||||
required bytes kek = 0xa; // idx=0 offset=c size=f
|
||||
required bytes kek = 0xa;
|
||||
}
|
||||
|
||||
// size=20
|
||||
|
||||
message FingerprintHmacRipemdChallenge {
|
||||
required bytes challenge = 0xa; // idx=0 offset=c size=13
|
||||
required bytes challenge = 0xa;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message PoWChallengeUnion {
|
||||
optional PoWHashCashChallenge hash_cash = 0xa; // idx=0 offset=c
|
||||
optional PoWHashCashChallenge hash_cash = 0xa;
|
||||
}
|
||||
|
||||
// size=24
|
||||
message PoWHashCashChallenge {
|
||||
optional bytes prefix = 0xa; // idx=0 offset=c size=f
|
||||
optional int32 length = 0x14; // idx=1 offset=1c type=int8
|
||||
optional int32 target = 0x1e; // idx=2 offset=20
|
||||
optional bytes prefix = 0xa;
|
||||
optional int32 length = 0x14;
|
||||
optional int32 target = 0x1e;
|
||||
}
|
||||
|
||||
// size=14
|
||||
|
||||
message CryptoChallengeUnion {
|
||||
optional CryptoShannonChallenge shannon = 0xa; // idx=0 offset=c
|
||||
optional CryptoRc4Sha1HmacChallenge rc4_sha1_hmac = 0x14; // idx=1 offset=10
|
||||
optional CryptoShannonChallenge shannon = 0xa;
|
||||
optional CryptoRc4Sha1HmacChallenge rc4_sha1_hmac = 0x14;
|
||||
}
|
||||
|
||||
// size=8
|
||||
|
||||
message CryptoShannonChallenge {
|
||||
}
|
||||
|
||||
// size=8
|
||||
|
||||
message CryptoRc4Sha1HmacChallenge {
|
||||
}
|
||||
|
||||
// size=18
|
||||
|
||||
message UpgradeRequiredMessage {
|
||||
required bytes upgrade_signed_part = 0xa; // idx=0 offset=c
|
||||
required bytes signature = 0x14; // idx=1 offset=10
|
||||
optional string http_suffix = 0x1e; // idx=2 offset=14
|
||||
required bytes upgrade_signed_part = 0xa;
|
||||
required bytes signature = 0x14;
|
||||
optional string http_suffix = 0x1e;
|
||||
}
|
||||
|
||||
// size=1c
|
||||
message APLoginFailed {
|
||||
required ErrorCode error_code = 0xa; // idx=0 offset=c
|
||||
optional int32 retry_delay = 0x14; // idx=1 offset=10
|
||||
optional int32 expiry = 0x1e; // idx=2 offset=14
|
||||
optional string error_description = 0x28; // idx=3 offset=18
|
||||
required ErrorCode error_code = 0xa;
|
||||
optional int32 retry_delay = 0x14;
|
||||
optional int32 expiry = 0x1e;
|
||||
optional string error_description = 0x28;
|
||||
}
|
||||
|
||||
enum ErrorCode {
|
||||
|
@ -190,50 +183,45 @@ enum ErrorCode {
|
|||
ApplicationBanned = 0x11;
|
||||
}
|
||||
|
||||
|
||||
|
||||
// size=18
|
||||
message ClientResponsePlaintext {
|
||||
required LoginCryptoResponseUnion login_crypto_response = 0xa; // idx=0 offset=c
|
||||
required PoWResponseUnion pow_response = 0x14; // idx=1 offset=10
|
||||
required CryptoResponseUnion crypto_response = 0x1e; // idx=2 offset=14
|
||||
required LoginCryptoResponseUnion login_crypto_response = 0xa;
|
||||
required PoWResponseUnion pow_response = 0x14;
|
||||
required CryptoResponseUnion crypto_response = 0x1e;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message LoginCryptoResponseUnion {
|
||||
optional LoginCryptoDiffieHellmanResponse diffie_hellman = 0xa; // idx=0 offset=c
|
||||
optional LoginCryptoDiffieHellmanResponse diffie_hellman = 0xa;
|
||||
}
|
||||
|
||||
// size=20
|
||||
|
||||
message LoginCryptoDiffieHellmanResponse {
|
||||
required bytes hmac = 0xa; // idx=0 offset=c size=13
|
||||
required bytes hmac = 0xa;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message PoWResponseUnion {
|
||||
optional PoWHashCashResponse hash_cash = 0xa; // idx=0 offset=c
|
||||
optional PoWHashCashResponse hash_cash = 0xa;
|
||||
}
|
||||
|
||||
// size=1c
|
||||
|
||||
message PoWHashCashResponse {
|
||||
required bytes hash_suffix = 0xa; // idx=0 offset=c size=f
|
||||
required bytes hash_suffix = 0xa;
|
||||
}
|
||||
|
||||
// size=14
|
||||
|
||||
message CryptoResponseUnion {
|
||||
optional CryptoShannonResponse shannon = 0xa; // idx=0 offset=c
|
||||
optional CryptoRc4Sha1HmacResponse rc4_sha1_hmac = 0x14; // idx=1 offset=10
|
||||
optional CryptoShannonResponse shannon = 0xa;
|
||||
optional CryptoRc4Sha1HmacResponse rc4_sha1_hmac = 0x14;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message CryptoShannonResponse {
|
||||
optional int32 dummy = 0x1; // idx=0 offset=c type=uint8
|
||||
optional int32 dummy = 0x1;
|
||||
}
|
||||
|
||||
// size=10
|
||||
|
||||
message CryptoRc4Sha1HmacResponse {
|
||||
optional int32 dummy = 0x1; // idx=0 offset=c type=uint8
|
||||
optional int32 dummy = 0x1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
|
23
src/main.rs
23
src/main.rs
|
@ -44,6 +44,7 @@ use protobuf::core::Message;
|
|||
use metadata::{MetadataCache, AlbumRef, ArtistRef, TrackRef};
|
||||
use session::{Config, Session};
|
||||
use util::SpotifyId;
|
||||
use util::version::version_string;
|
||||
use player::Player;
|
||||
use mercury::{MercuryRequest, MercuryMethod};
|
||||
use librespot_protocol as protocol;
|
||||
|
@ -53,28 +54,31 @@ fn main() {
|
|||
let mut appkey_file = File::open(Path::new(&args.next().unwrap())).unwrap();
|
||||
let username = args.next().unwrap();
|
||||
let password = args.next().unwrap();
|
||||
let name = args.next().unwrap();
|
||||
|
||||
let mut appkey = Vec::new();
|
||||
appkey_file.read_to_end(&mut appkey).unwrap();
|
||||
|
||||
let config = Config {
|
||||
application_key: appkey,
|
||||
user_agent: "ABC".to_string(),
|
||||
device_id: "ABC".to_string()
|
||||
user_agent: version_string(),
|
||||
device_id: name.to_string()
|
||||
};
|
||||
let session = Session::new(config);
|
||||
session.login(username, password);
|
||||
session.login(username.clone(), password);
|
||||
session.poll();
|
||||
|
||||
let ident = session.config.device_id.clone();
|
||||
SpircManager{
|
||||
session: session,
|
||||
username: username.clone(),
|
||||
name: name.clone(),
|
||||
ident: ident,
|
||||
device_type: 5,
|
||||
|
||||
state_update_id: 0,
|
||||
seq_nr: 0,
|
||||
|
||||
name: "BlaBla".to_string(),
|
||||
ident: ident,
|
||||
device_type: 5,
|
||||
volume: 0x8000,
|
||||
can_play: true,
|
||||
is_active: false,
|
||||
|
@ -116,6 +120,7 @@ fn print_track(cache: &mut MetadataCache, track_id: SpotifyId) {
|
|||
|
||||
struct SpircManager {
|
||||
session: Session,
|
||||
username: String,
|
||||
state_update_id: i64,
|
||||
seq_nr: u32,
|
||||
|
||||
|
@ -135,7 +140,7 @@ impl SpircManager {
|
|||
|
||||
self.session.mercury.send(MercuryRequest{
|
||||
method: MercuryMethod::SUB,
|
||||
uri: "hm://remote/user/lietar/v23".to_string(),
|
||||
uri: format!("hm://remote/user/{}/v23", self.username).to_string(),
|
||||
content_type: None,
|
||||
callback: Some(tx),
|
||||
payload: Vec::new()
|
||||
|
@ -185,7 +190,7 @@ impl SpircManager {
|
|||
let device_state = self.device_state();
|
||||
self.session.mercury.send(MercuryRequest{
|
||||
method: MercuryMethod::SEND,
|
||||
uri: "hm://remote/user/lietar".to_string(),
|
||||
uri: format!("hm://remote/user/{}", self.username).to_string(),
|
||||
content_type: None,
|
||||
callback: None,
|
||||
payload: vec![
|
||||
|
@ -206,7 +211,7 @@ impl SpircManager {
|
|||
|
||||
fn device_state(&mut self) -> protocol::spirc::DeviceState {
|
||||
protobuf_init!(protocol::spirc::DeviceState::new(), {
|
||||
sw_version: "librespot-0.1.0".to_string(),
|
||||
sw_version: version_string(),
|
||||
is_active: self.is_active,
|
||||
can_play: self.can_play,
|
||||
volume: self.volume as u32,
|
||||
|
|
|
@ -147,7 +147,7 @@ impl Session {
|
|||
let packet = protobuf_init!(protocol::authentication::ClientResponseEncrypted::new(), {
|
||||
login_credentials => {
|
||||
username: username,
|
||||
typ: protocol::authentication::Type::AUTHENTICATION_USER_PASS,
|
||||
typ: protocol::authentication::AuthenticationType::AUTHENTICATION_USER_PASS,
|
||||
auth_data: password.into_bytes(),
|
||||
},
|
||||
system_info => {
|
||||
|
|
Loading…
Reference in a new issue