-- This file is part of Bindings-bfd. -- -- Copyright (C) 2010 Michael Nelson -- -- Bindings-bfd is free software: you can redistribute it and/or modify -- it under the terms of the GNU Lesser General Public License as published by -- the Free Software Foundation, either version 3 of the License, or -- (at your option) any later version. -- -- Bindings-bfd is distributed in the hope that it will be useful, -- but WITHOUT ANY WARRANTY; without even the implied warranty of -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -- GNU Lesser General Public License for more details. -- You should have received a copy of the GNU Lesser General Public License -- along with Bindings-bfd. If not, see . {-# LANGUAGE DeriveDataTypeable #-} module Bindings.Bfd.Exception where import Control.Exception import Data.Typeable import Foreign.C import Foreign.Ptr import Bindings.Bfd.Target type FunctionName = String type FormatName = String type ErrorMsg = String data BfdException = NoError FunctionName FilePath TargetName | SystemCall FunctionName FilePath TargetName ErrorMsg | InvalidTarget FunctionName FilePath TargetName | WrongFormat | WrongObjectFormat | InvalidOperation | NoMemory | NoSymbols | NoArmap | NoMoreArchivedFiles | MalformedArchive | FileNotRecognized FunctionName FormatName | FileAmbiguouslyRecognized | NoContents | NonrepresentableSection | NoDebugSection | BadValue | FileTruncated | FileTooBig | OnInput | InvalidErrorCode deriving (Typeable) instance Show BfdException where show (NoError fn fp tn ) = fp ++ ": " ++ fn ++ ": '" ++ tn ++ "': no error (report this as a bug)" show (SystemCall fn fp tn msg) = fp ++ ": " ++ fn ++ ": '" ++ tn ++ "': system call (" ++ msg ++ ")" show (InvalidTarget fn fp tn ) = fp ++ ": " ++ fn ++ ": '" ++ tn ++ "': invalid target" show (WrongFormat ) = "3" show (WrongObjectFormat ) = "4" show (InvalidOperation ) = "5" show (NoMemory ) = "6" show (NoSymbols ) = "7" show (NoArmap ) = "8" show (NoMoreArchivedFiles ) = "9" show (MalformedArchive ) = "10" show (FileNotRecognized fn ff ) = ff ++ ": " ++ fn ++ ": " ++ "file format not recognized" show (FileAmbiguouslyRecognized ) = "12" show (NoContents ) = "13" show (NonrepresentableSection ) = "14" show (NoDebugSection ) = "15" show (BadValue ) = "16" show (FileTruncated ) = "17" show (FileTooBig ) = "18" show (OnInput ) = "19" show (InvalidErrorCode ) = "20" instance Exception BfdException where throwExceptionIfNull :: FunctionName -> FilePath -> TargetName -> IO (Ptr a) -> IO (Ptr a) throwExceptionIfNull fn fp tn f = do res <- f if res == nullPtr then throwException fn fp tn else return res throwExceptionIfFalse :: FunctionName -> FormatName -> IO Bool -> IO Bool throwExceptionIfFalse fn ff f = do res <- f if res == False then throwException fn ff "" else return res throwException :: String -> String -> String -> IO a throwException s1 s2 s3 = do errNum <- c_bfd_get_error errMsg <- peekCString (c_bfd_errmsg errNum) let e = case errNum of 0 -> NoError s1 s2 s3 1 -> SystemCall s1 s2 s3 errMsg 2 -> InvalidTarget s1 s2 s3 3 -> WrongFormat 4 -> WrongObjectFormat 5 -> InvalidOperation 6 -> NoMemory 7 -> NoSymbols 8 -> NoArmap 9 -> NoMoreArchivedFiles 10 -> MalformedArchive 11 -> FileNotRecognized s1 s2 12 -> FileAmbiguouslyRecognized 13 -> NoContents 14 -> NonrepresentableSection 15 -> NoDebugSection 16 -> BadValue 17 -> FileTruncated 18 -> FileTooBig 19 -> OnInput _ -> InvalidErrorCode throwIO e foreign import ccall unsafe "bfd.h bfd_get_error" c_bfd_get_error :: IO CInt foreign import ccall unsafe "bfd.h bfd_errmsg" c_bfd_errmsg :: CInt -> CString