forked from schmittlauch/Hash2Pub
better error handling in ASN.1 message parser
This commit is contained in:
parent
6dc9650da5
commit
28254a9f83
|
@ -284,12 +284,17 @@ encodeMessage
|
||||||
|
|
||||||
parseMessage :: ParseASN1 FediChordMessage
|
parseMessage :: ParseASN1 FediChordMessage
|
||||||
parseMessage = do
|
parseMessage = do
|
||||||
|
begin <- getNext
|
||||||
|
case begin of
|
||||||
|
Start Sequence -> return ()
|
||||||
|
x -> throwParseError $ "unexpected ASN.1 element " ++ show x
|
||||||
-- request and response messages are distiguishable by their structure,
|
-- request and response messages are distiguishable by their structure,
|
||||||
-- see ASN.1 schema
|
-- see ASN.1 schema
|
||||||
first <- getNext
|
first <- getNext
|
||||||
case first of
|
case first of
|
||||||
Enumerated a -> parseRequest . toEnum . fromIntegral $ a
|
Enumerated a -> parseRequest . toEnum . fromIntegral $ a
|
||||||
IntVal i -> parseResponse i
|
IntVal i -> parseResponse i
|
||||||
|
other -> throwParseError $ "unexpected first ASN1 element: " ++ show other
|
||||||
|
|
||||||
parseRequest :: Action -> ParseASN1 FediChordMessage
|
parseRequest :: Action -> ParseASN1 FediChordMessage
|
||||||
parseRequest action = do
|
parseRequest action = do
|
||||||
|
@ -304,6 +309,11 @@ parseRequest action = do
|
||||||
Leave -> parseLeaveRequest
|
Leave -> parseLeaveRequest
|
||||||
Stabilise -> parseStabiliseRequest
|
Stabilise -> parseStabiliseRequest
|
||||||
Ping -> parsePingRequest
|
Ping -> parsePingRequest
|
||||||
|
-- consume sequence end
|
||||||
|
end <- getNext
|
||||||
|
case end of
|
||||||
|
End Sequence -> return ()
|
||||||
|
x -> throwParseError $ "unexpected ASN.1 element " ++ show x
|
||||||
|
|
||||||
return $ Request requestID sender parts part action payload
|
return $ Request requestID sender parts part action payload
|
||||||
|
|
||||||
|
@ -320,35 +330,48 @@ parseResponse responseTo = do
|
||||||
Leave -> parseLeaveResponse
|
Leave -> parseLeaveResponse
|
||||||
Stabilise -> parseStabiliseResponse
|
Stabilise -> parseStabiliseResponse
|
||||||
Ping -> parsePingResponse
|
Ping -> parsePingResponse
|
||||||
|
-- consume sequence end
|
||||||
|
end <- getNext
|
||||||
|
case end of
|
||||||
|
End Sequence -> return ()
|
||||||
|
x -> throwParseError $ "unexpected ASN.1 element " ++ show x
|
||||||
|
|
||||||
return $ Response responseTo senderID parts part action payload
|
return $ Response responseTo senderID parts part action payload
|
||||||
|
|
||||||
parseInteger :: ParseASN1 Integer
|
parseInteger :: ParseASN1 Integer
|
||||||
parseInteger = do
|
parseInteger = do
|
||||||
IntVal parsed <- getNext
|
i <- getNext
|
||||||
return parsed
|
case i of
|
||||||
|
IntVal parsed -> return parsed
|
||||||
|
x -> throwParseError $ "Expected IntVal but got " ++ show x
|
||||||
|
|
||||||
parseEnum :: Enum a => ParseASN1 a
|
parseEnum :: Enum a => ParseASN1 a
|
||||||
parseEnum = do
|
parseEnum = do
|
||||||
Enumerated en <- getNext
|
e <- getNext
|
||||||
return $ toEnum . fromIntegral $ en
|
case e of
|
||||||
|
Enumerated en -> return $ toEnum . fromIntegral $ en
|
||||||
|
x -> throwParseError $ "Expected Enumerated but got " ++ show x
|
||||||
|
|
||||||
parseString :: ParseASN1 String
|
parseString :: ParseASN1 String
|
||||||
parseString = do
|
parseString = do
|
||||||
ASN1String toBeParsed <- getNext
|
s <- getNext
|
||||||
maybe (throwParseError "string parsing failed") return $ asn1CharacterToString toBeParsed
|
case s of
|
||||||
|
ASN1String toBeParsed -> maybe (throwParseError "string parsing failed") return $ asn1CharacterToString toBeParsed
|
||||||
|
x -> throwParseError $ "Expected a ASN1String but got " ++ show x
|
||||||
|
|
||||||
parseOctets :: ParseASN1 BS.ByteString
|
parseOctets :: ParseASN1 BS.ByteString
|
||||||
parseOctets = do
|
parseOctets = do
|
||||||
OctetString bs <- getNext
|
os <- getNext
|
||||||
return bs
|
case os of
|
||||||
|
OctetString bs -> return bs
|
||||||
|
x -> throwParseError $ "Expected an OctetString but got " ++ show x
|
||||||
|
|
||||||
parseNull :: ParseASN1 ()
|
parseNull :: ParseASN1 ()
|
||||||
parseNull = do
|
parseNull = do
|
||||||
-- ToDo: figure out how this fails on wrong inputs,
|
n <- getNext
|
||||||
-- maybe a case distinction + throwParseError is better?
|
case n of
|
||||||
Null <- getNext
|
Null -> return ()
|
||||||
return ()
|
x -> throwParseError $ "Expected Null but got " ++ show x
|
||||||
|
|
||||||
parseNodeState :: ParseASN1 NodeState
|
parseNodeState :: ParseASN1 NodeState
|
||||||
parseNodeState = do
|
parseNodeState = do
|
||||||
|
|
Loading…
Reference in a new issue