Is a nonce considered 'secret' enough for HMAC? We're implementing a mobile application which communicates with a web service, and on first install the user sends its deviceid to the web service (over TLS, unauthenticated at this point) - which determines if the user's device is known to our system. If the device is not known, the user must authenticate with a username and password to associate the device. When the web service responds to the mobile application requesting a username and password, the response includes a nonce, valid for that request and response only.

Once the Username/Password is requested, the client generates a cnonce and a HMAC:

hash_hmac(sha256, nonce || deviceid || cnonce, nonce) 


using the nonce supplied previously as the key. When the response is received by the web service, the supplied nonce is invalidated.

As this mobile app is considered to be on a hostile device, we don't want to be storing a secret key in the app which can be recovered.

Is it safe to use the nonce as the key for the hmac in the above example?
No, the nonce is not fit to be a HMAC key, because anybody can view the nonce in transit. If - on the other hand - the TLS connection does deliver enough security then you would not need the HMAC.

It's fine to use the nonce as one time code, but you don't need the HMAC for that. If an attacker can obtain nonce's send to clients than the attacker can always replace the original nonce with another one by redoing the HMAC calculations.

Note that your solution space may be empty if you cannot trust the client application. That sounds a lot like trying to implement a DRM scheme.