-
Notifications
You must be signed in to change notification settings - Fork 160
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
ASN1 decoding: how to ignore padding? #91
Comments
Because |
not exactly me, but it's the result of decrypting an SNMPv3 encrypted PDU. I'm also using openssl for the decryption, and am explicitly setting the padding to 0, as specified in the rfc. Along these lines: cipher = Cipher::DES.new(:CBC)
cipher.decrypt
cipher.padding = 0
cipher.key = key
cipher.iv = iv
data = cipher.update(encrypted_pdu) + cipher.final
# data was padded before encryption, so a BER-encoded PDU might have length 77, while the decrypted
# part might be length 80
# what to do here to safely remove padding before decoding? And this is my question. Right now, I'm slicing all The example I gave you might not be a valid BER encoding, but I thought there could be an hidden API which would ignore bytes which aren't part of a BER-encoded sequence, and so on, like: stream = "0\x03\x02\x01\x00\x02\x01\x00"
OpenSSL::ASN1.decode stream This will fail with a type mismatch error, but it also could just decode the sequence and ignore the subsequence integer, with, let's say, an imaginary argument Anyway, this is just an idea. I'd totally understand if this weren't to be supported, and would appreciate any kind of suggestions you'd have on remove padding from deciphered payloads, as I don't have currently any idea on how to do that besides the faulty patch I mentioned above. |
The protocol doesn't seem to give the actual content length. That's unfortunate. I however think such an option is useful in too limited situations to provide from the openssl library. In this case, I think you can workaround by inspecting the real content length with OpenSSL::ASN1.traverse[1]: str = "\x02\x01\x00\x00"
headerlen, bodylen = OpenSSL::ASN1.traverse(str) { |_, _, x, y, *| break x, y }
decoded = OpenSSL::ASN1.decode(str.byteslice(0, headerlen+bodylen)) [1] http://ruby.github.io/openssl/OpenSSL/ASN1.html#method-c-traverse |
The protocol does give the content length (in that case, it's an integer with size 1 and value 0, it would work the same for sequences). You need to decode it first, however. It is possible, and something that the library could do, but you know the situations in which this part of openssl is used better than me. The workaround with traverse does seem to solve my issue. I'll have a quick try in a few minutes and will let you know. Thx for the tip! |
It did the trick. Thx Again! |
I'm using the ASN1 to decode information which had been previously encrypted. It was decrypted also using openssl (DES interface), and it came out padded. Let's say, for the sake of argument, the stream was
\x02\x01\x00\x00
, where the last\x00
is padding. I'd expect to callASN1.decode
and have it decode it to the integer, but instead it fails:Is there a way to accomplish this? Or am I forced to inspect the length bytes and remove the padding myself?
The text was updated successfully, but these errors were encountered: