Skip to content

Commit c1bba6f

Browse files
committed
Merge #410: Implement source for error types
5935d86 Implement error::Error for all error types (Tobin C. Harding) a5db0f0 Re-order error code blocks (Tobin C. Harding) 2eac9de Remove error::Error::description (Tobin C. Harding) 3bdeb8c Move SigType down the file (Tobin C. Harding) Pull request description: Now we have MSRV of 1.41.1 we can implement `source` for improved error handling. Patches 1-3 are preparatory cleanup, patch 4 adds all the `source` impls. Resolves: #273 ACKs for top commit: apoelstra: ACK 5935d86 sanket1729: ACK 5935d86. Checked that all changes correctly pass through the source. Did not check whether there are more Error types that are not covered. Tree-SHA512: f74f0bfabba92dab6e88d26ec098a60c66eae8cbbad34433ef0f95c42d1d79352d1a408506e604b5564c0e4b15ed3a7e41ffe1d2fd1ba127b66bdba287091357
2 parents 832fc8e + 5935d86 commit c1bba6f

File tree

11 files changed

+431
-222
lines changed

11 files changed

+431
-222
lines changed

src/descriptor/key.rs

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -219,7 +219,11 @@ impl fmt::Display for DescriptorKeyParseError {
219219
}
220220
}
221221

222-
impl error::Error for DescriptorKeyParseError {}
222+
impl error::Error for DescriptorKeyParseError {
223+
fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
224+
None
225+
}
226+
}
223227

224228
impl fmt::Display for DescriptorPublicKey {
225229
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -369,7 +373,15 @@ impl fmt::Display for ConversionError {
369373
}
370374
}
371375

372-
impl error::Error for ConversionError {}
376+
impl error::Error for ConversionError {
377+
fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
378+
use self::ConversionError::*;
379+
380+
match self {
381+
Wildcard | HardenedChild | HardenedWildcard => None,
382+
}
383+
}
384+
}
373385

374386
impl DescriptorPublicKey {
375387
/// The fingerprint of the master key associated with this key, `0x00000000` if none.

src/interpreter/error.rs

Lines changed: 109 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -118,78 +118,6 @@ pub enum Error {
118118
VerifyFailed,
119119
}
120120

121-
/// A type of representing which keys errored during interpreter checksig evaluation
122-
// Note that we can't use BitcoinKey because it is not public
123-
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
124-
pub enum PkEvalErrInner {
125-
/// Full Key
126-
FullKey(bitcoin::PublicKey),
127-
/// XOnly Key
128-
XOnlyKey(bitcoin::XOnlyPublicKey),
129-
}
130-
131-
impl From<BitcoinKey> for PkEvalErrInner {
132-
fn from(pk: BitcoinKey) -> Self {
133-
match pk {
134-
BitcoinKey::Fullkey(pk) => PkEvalErrInner::FullKey(pk),
135-
BitcoinKey::XOnlyPublicKey(xpk) => PkEvalErrInner::XOnlyKey(xpk),
136-
}
137-
}
138-
}
139-
140-
impl fmt::Display for PkEvalErrInner {
141-
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
142-
match self {
143-
PkEvalErrInner::FullKey(pk) => pk.fmt(f),
144-
PkEvalErrInner::XOnlyKey(xpk) => xpk.fmt(f),
145-
}
146-
}
147-
}
148-
149-
#[doc(hidden)]
150-
impl From<secp256k1::Error> for Error {
151-
fn from(e: secp256k1::Error) -> Error {
152-
Error::Secp(e)
153-
}
154-
}
155-
156-
#[doc(hidden)]
157-
impl From<bitcoin::util::sighash::Error> for Error {
158-
fn from(e: bitcoin::util::sighash::Error) -> Error {
159-
Error::SighashError(e)
160-
}
161-
}
162-
163-
#[doc(hidden)]
164-
impl From<bitcoin::EcdsaSigError> for Error {
165-
fn from(e: bitcoin::EcdsaSigError) -> Error {
166-
Error::EcdsaSig(e)
167-
}
168-
}
169-
170-
#[doc(hidden)]
171-
impl From<bitcoin::SchnorrSigError> for Error {
172-
fn from(e: bitcoin::SchnorrSigError) -> Error {
173-
Error::SchnorrSig(e)
174-
}
175-
}
176-
177-
#[doc(hidden)]
178-
impl From<crate::Error> for Error {
179-
fn from(e: crate::Error) -> Error {
180-
Error::Miniscript(e)
181-
}
182-
}
183-
184-
impl error::Error for Error {
185-
fn cause(&self) -> Option<&dyn error::Error> {
186-
match *self {
187-
Error::Secp(ref err) => Some(err),
188-
ref x => Some(x),
189-
}
190-
}
191-
}
192-
193121
impl fmt::Display for Error {
194122
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
195123
match *self {
@@ -263,3 +191,112 @@ impl fmt::Display for Error {
263191
}
264192
}
265193
}
194+
195+
impl error::Error for Error {
196+
fn cause(&self) -> Option<&dyn error::Error> {
197+
use self::Error::*;
198+
199+
match self {
200+
AbsoluteLocktimeNotMet(_)
201+
| CannotInferTrDescriptors
202+
| ControlBlockVerificationError
203+
| CouldNotEvaluate
204+
| ExpectedPush
205+
| HashPreimageLengthMismatch
206+
| IncorrectPubkeyHash
207+
| IncorrectScriptHash
208+
| IncorrectWPubkeyHash
209+
| IncorrectWScriptHash
210+
| InsufficientSignaturesMultiSig
211+
| InvalidEcdsaSignature(_)
212+
| InvalidSchnorrSignature(_)
213+
| InvalidSchnorrSighashType(_)
214+
| NonStandardSighash(_)
215+
| MissingExtraZeroMultiSig
216+
| MultiSigEvaluationError
217+
| NonEmptyWitness
218+
| NonEmptyScriptSig
219+
| PubkeyParseError
220+
| XOnlyPublicKeyParseError
221+
| PkEvaluationError(_)
222+
| PkHashVerifyFail(_)
223+
| RelativeLocktimeNotMet(_)
224+
| ScriptSatisfactionError
225+
| TapAnnexUnsupported
226+
| UncompressedPubkey
227+
| UnexpectedStackBoolean
228+
| UnexpectedStackEnd
229+
| UnexpectedStackElementPush
230+
| VerifyFailed => None,
231+
ControlBlockParse(e) => Some(e),
232+
EcdsaSig(e) => Some(e),
233+
Miniscript(e) => Some(e),
234+
Secp(e) => Some(e),
235+
SchnorrSig(e) => Some(e),
236+
SighashError(e) => Some(e),
237+
}
238+
}
239+
}
240+
241+
#[doc(hidden)]
242+
impl From<secp256k1::Error> for Error {
243+
fn from(e: secp256k1::Error) -> Error {
244+
Error::Secp(e)
245+
}
246+
}
247+
248+
#[doc(hidden)]
249+
impl From<bitcoin::util::sighash::Error> for Error {
250+
fn from(e: bitcoin::util::sighash::Error) -> Error {
251+
Error::SighashError(e)
252+
}
253+
}
254+
255+
#[doc(hidden)]
256+
impl From<bitcoin::EcdsaSigError> for Error {
257+
fn from(e: bitcoin::EcdsaSigError) -> Error {
258+
Error::EcdsaSig(e)
259+
}
260+
}
261+
262+
#[doc(hidden)]
263+
impl From<bitcoin::SchnorrSigError> for Error {
264+
fn from(e: bitcoin::SchnorrSigError) -> Error {
265+
Error::SchnorrSig(e)
266+
}
267+
}
268+
269+
#[doc(hidden)]
270+
impl From<crate::Error> for Error {
271+
fn from(e: crate::Error) -> Error {
272+
Error::Miniscript(e)
273+
}
274+
}
275+
276+
/// A type of representing which keys errored during interpreter checksig evaluation
277+
// Note that we can't use BitcoinKey because it is not public
278+
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
279+
pub enum PkEvalErrInner {
280+
/// Full Key
281+
FullKey(bitcoin::PublicKey),
282+
/// XOnly Key
283+
XOnlyKey(bitcoin::XOnlyPublicKey),
284+
}
285+
286+
impl From<BitcoinKey> for PkEvalErrInner {
287+
fn from(pk: BitcoinKey) -> Self {
288+
match pk {
289+
BitcoinKey::Fullkey(pk) => PkEvalErrInner::FullKey(pk),
290+
BitcoinKey::XOnlyPublicKey(xpk) => PkEvalErrInner::XOnlyKey(xpk),
291+
}
292+
}
293+
}
294+
295+
impl fmt::Display for PkEvalErrInner {
296+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
297+
match self {
298+
PkEvalErrInner::FullKey(pk) => pk.fmt(f),
299+
PkEvalErrInner::XOnlyKey(xpk) => xpk.fmt(f),
300+
}
301+
}
302+
}

0 commit comments

Comments
 (0)