dhscanner-kbgen 1.0.25 → 1.0.26
raw patch · 2 files changed
+174/−31 lines, 2 filesdep ~dhscanner-astdep ~dhscanner-bitcodePVP: major bump suggested
API removals or changes: PVP suggests a major version bump
Dependency ranges changed: dhscanner-ast, dhscanner-bitcode
API changes (from Hackage documentation)
- Kbgen: ArgForCall :: Arg -> Call -> ArgForCall
- Kbgen: ArgForCallCtor :: ArgForCall -> Fact
- Kbgen: data ArgForCall
- Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.ArgForCall
- Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.ArgForCall
- Kbgen: instance GHC.Classes.Eq Kbgen.ArgForCall
- Kbgen: instance GHC.Classes.Ord Kbgen.ArgForCall
- Kbgen: instance GHC.Generics.Generic Kbgen.ArgForCall
- Kbgen: instance GHC.Show.Show Kbgen.ArgForCall
+ Kbgen: Call1stPartyFuncDefinedInDir :: Call -> FuncName -> FuncDefinedInDir -> Call1stPartyFuncDefinedInDir
+ Kbgen: FuncDef :: Func -> FuncName -> FuncDefinedInFile -> FuncDefinedInDir -> FuncDef
+ Kbgen: FuncDefinedInDir :: FilePath -> FuncDefinedInDir
+ Kbgen: FuncDefinedInFile :: FilePath -> FuncDefinedInFile
+ Kbgen: FuncName :: String -> FuncName
+ Kbgen: data Call1stPartyFuncDefinedInDir
+ Kbgen: data FuncDef
+ Kbgen: data FuncDefinedInDir
+ Kbgen: data FuncDefinedInFile
+ Kbgen: data FuncName
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.Func
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.FuncDef
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.FuncDefinedInDir
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.FuncDefinedInFile
+ Kbgen: instance Data.Aeson.Types.FromJSON.FromJSON Kbgen.FuncName
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.Func
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.FuncDef
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.FuncDefinedInDir
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.FuncDefinedInFile
+ Kbgen: instance Data.Aeson.Types.ToJSON.ToJSON Kbgen.FuncName
+ Kbgen: instance GHC.Classes.Eq Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance GHC.Classes.Eq Kbgen.Func
+ Kbgen: instance GHC.Classes.Eq Kbgen.FuncDef
+ Kbgen: instance GHC.Classes.Eq Kbgen.FuncDefinedInDir
+ Kbgen: instance GHC.Classes.Eq Kbgen.FuncDefinedInFile
+ Kbgen: instance GHC.Classes.Eq Kbgen.FuncName
+ Kbgen: instance GHC.Classes.Ord Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance GHC.Classes.Ord Kbgen.Func
+ Kbgen: instance GHC.Classes.Ord Kbgen.FuncDef
+ Kbgen: instance GHC.Classes.Ord Kbgen.FuncDefinedInDir
+ Kbgen: instance GHC.Classes.Ord Kbgen.FuncDefinedInFile
+ Kbgen: instance GHC.Classes.Ord Kbgen.FuncName
+ Kbgen: instance GHC.Generics.Generic Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance GHC.Generics.Generic Kbgen.Func
+ Kbgen: instance GHC.Generics.Generic Kbgen.FuncDef
+ Kbgen: instance GHC.Generics.Generic Kbgen.FuncDefinedInDir
+ Kbgen: instance GHC.Generics.Generic Kbgen.FuncDefinedInFile
+ Kbgen: instance GHC.Generics.Generic Kbgen.FuncName
+ Kbgen: instance GHC.Show.Show Kbgen.Call1stPartyFuncDefinedInDir
+ Kbgen: instance GHC.Show.Show Kbgen.Func
+ Kbgen: instance GHC.Show.Show Kbgen.FuncDef
+ Kbgen: instance GHC.Show.Show Kbgen.FuncDefinedInDir
+ Kbgen: instance GHC.Show.Show Kbgen.FuncDefinedInFile
+ Kbgen: instance GHC.Show.Show Kbgen.FuncName
Files
- dhscanner-kbgen.cabal +3/−3
- src/Kbgen.hs +171/−28
dhscanner-kbgen.cabal view
@@ -33,7 +33,7 @@ * explain in plain English your query's purpose * et voilà ! -version: 1.0.25 +version: 1.0.26 license: GPL-3.0-only license-file: LICENSE author: OrenGitHub @@ -59,8 +59,8 @@ aeson < 2.3, base >= 4.18 && < 4.19, containers < 0.7, - dhscanner-ast >= 1.1.4, - dhscanner-bitcode >= 1.0.14 + dhscanner-ast >= 1.1.5, + dhscanner-bitcode >= 1.0.16 hs-source-dirs: src
src/Kbgen.hs view
@@ -55,10 +55,11 @@ KeywordArgForCall(..), ParamResolvedType(..), ClassDef(..), + FuncDef(..), + Call1stPartyFuncDefinedInDir(..), ParamName(..), CallMethodOfClass(..), ConstString(..), - ArgForCall(..), MethodOfClass(..), ClassHas1stPartySuper(..), ClassHas3rdPartySuper(..), @@ -82,10 +83,13 @@ Resolved(..), ArgIndex(..), ParamIndex(..), + FuncName(..), MethodName(..), ResolvedType(..), CallResolved(..), ResolvedSuper(..), + FuncDefinedInFile(..), + FuncDefinedInDir(..), ClassDefinedInFile(..), SuperDefinedInFile(..), SuperQualifiedName(..), @@ -235,6 +239,116 @@ -- | -- +-- __Name__ +-- +-- This is how the fact will look inside the Prolog file +-- +-- @ +-- kb_func_def( Func, Name, DefinedInFile ). +-- @ +-- +-- __When should I use this fact__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) +-- +-- @ +-- # http_getter.go +-- g.GET("/get/httpmeta", func(c echo.Context) error { +-- urlStr := c.QueryParam("url") +-- ... +-- getter.GetHTMLMeta(urlStr) +-- +-- # html_meta.go +-- func GetHTMLMeta(urlStr string) (*HTMLMeta, error) { +-- ... +-- http.Get(urlStr) +-- @ +-- +-- See complete source example [here](https://github.com/usememos/memos/blob/v0.14.0/api/v1/http_getter.go#L23), +-- and [here](https://github.com/usememos/memos/blob/v0.14.0/plugin/http-getter/html_meta.go#L24) +-- +-- __Writing a predicate with this fact and others__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) +-- +-- @ +-- suspected_ssrf_sink( Func ) :- +-- kb_resolved_call( Call, \'net/http.Get\' ), +-- kb_arg_i_for_call( Arg, 0, Call ), +-- utils_dataflow_path( Param, Arg ), +-- kb_param_has_resolved_type( Param, \'string\' ), +-- kb_param_i_of_callable( Param, _, Func ), +-- kb_func_def( Func, Name, _, FuncDefinedInDir ), +-- kb_call_1st_party_func_defined_in_dir( _, Name, FuncDefinedInDir ). +-- @ +-- +-- Other facts combined in this predicate: +-- +-- * 'CallResolved' +-- * 'ArgiForCall' +-- * 'ParamResolvedType' +-- * 'ParamiOfCallable' +-- * 'Call1stPartyFuncDefinedInDir' +-- +data FuncDef = FuncDef + Func -- ^ + Token.FuncName -- ^ + FuncDefinedInFile -- ^ + FuncDefinedInDir -- ^ + deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) + +-- | +-- +-- __Name__ +-- +-- This is how the fact will look inside the Prolog file +-- +-- @ +-- kb_call_1st_party_func_defined_in_dir( Call, Name, DefinedInDir ). +-- @ +-- +-- __When should I use this fact__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) +-- +-- @ +-- # http_getter.go +-- g.GET("/get/httpmeta", func(c echo.Context) error { +-- urlStr := c.QueryParam("url") +-- ... +-- getter.GetHTMLMeta(urlStr) +-- +-- # html_meta.go +-- func GetHTMLMeta(urlStr string) (*HTMLMeta, error) { +-- ... +-- http.Get(urlStr) +-- @ +-- +-- See complete source example [here](https://github.com/usememos/memos/blob/v0.14.0/api/v1/http_getter.go#L23), +-- and [here](https://github.com/usememos/memos/blob/v0.14.0/plugin/http-getter/html_meta.go#L24) +-- +-- __Writing a predicate with this fact and others__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) +-- +-- @ +-- suspected_ssrf_sink( Func ) :- +-- kb_resolved_call( Call, \'net/http.Get\' ), +-- kb_arg_i_for_call( Arg, 0, Call ), +-- utils_dataflow_path( Param, Arg ), +-- kb_param_has_resolved_type( Param, \'string\' ), +-- kb_param_i_of_callable( Param, _, Func ), +-- kb_func_def( Func, Name, _, FuncDefinedInDir ), +-- kb_call_1st_party_func_from_dir( _, Name, FuncDefinedInDir ). +-- @ +-- +-- Other facts combined in this predicate: +-- +-- * 'CallResolved' +-- * 'ArgiForCall' +-- * 'ParamResolvedType' +-- * 'ParamiOfCallable' +-- +data Call1stPartyFuncDefinedInDir = Call1stPartyFuncDefinedInDir + Call -- ^ + FuncName -- ^ + FuncDefinedInDir -- ^ + deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) + +-- | +-- -- __Description:__ -- -- Input parameter of some callable ( method, function, lambda ) has the specified name @@ -555,8 +669,12 @@ -- -- ==== __Tip 💡__ -- --- sometimes the exact index is irrelevant, see 'ArgForCall' +-- When the exact index is irrelevant, use: -- +-- @ +-- kb_arg_i_for_call( Arg, _, Call ). +-- @ +-- data ArgiForCall = ArgiForCall Arg -- ^ ArgIndex -- ^ @@ -565,39 +683,73 @@ -- | -- --- Usage: +-- __Name__ -- +-- This is how the fact will look inside the Prolog file +-- -- @ --- arg_for_call( Arg, Call ). +-- kb_param_i_of_callable( Param, Index, Callable ). -- @ -- --- ==== __Tip 💡__ +-- __When should I use this fact__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) -- --- sometimes the exact index is irrelevant, see 'ArgForCall' +-- @ +-- # http_getter.go +-- g.GET("/get/httpmeta", func(c echo.Context) error { +-- urlStr := c.QueryParam("url") +-- ... +-- getter.GetHTMLMeta(urlStr) -- -data ArgForCall = ArgForCall - Arg -- ^ - Call -- ^ - deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) - --- | +-- # html_meta.go +-- func GetHTMLMeta(urlStr string) (*HTMLMeta, error) { +-- ... +-- http.Get(urlStr) +-- @ -- --- Usage: +-- See complete source example [here](https://github.com/usememos/memos/blob/v0.14.0/api/v1/http_getter.go#L23), +-- and [here](https://github.com/usememos/memos/blob/v0.14.0/plugin/http-getter/html_meta.go#L24) -- +-- __Writing a predicate with this fact and others__ ( motivation: [CVE-2024-29028](https://nvd.nist.gov/vuln/detail/CVE-2024-29028) ) +-- -- @ --- ParamiOfCallable( Param, Index, Callable ). +-- suspected_ssrf_sink( Func ) :- +-- kb_resolved_call( Call, \'net/http.Get\' ), +-- kb_arg_i_for_call( Arg, 0, Call ), +-- utils_dataflow_path( Param, Arg ), +-- kb_param_has_resolved_type( Param, \'string\' ), +-- kb_param_i_of_callable( Param, _, Func ), +-- kb_func_def( Func, Name, _, FuncDefinedInDir ), +-- kb_call_1st_party_func_defined_in_dir( _, Name, FuncDefinedInDir ). -- @ -- +-- Other facts combined in this predicate: +-- +-- * 'CallResolved' +-- * 'ArgiForCall' +-- * 'ParamResolvedType' +-- * 'FuncDef' +-- * 'Call1stPartyFuncDefinedInDir' +-- -- ==== __Tip 💡__ -- --- sometimes the exact index is irrelevant, see 'Arg_for_Call' +-- When the _exact index_ is _irrelevant_, use: -- +-- @ +-- kb_param_i_of_callable( Param, _, Callable ). +-- @ +-- data ParamiOfCallable = ParamiOfCallable Param -- ^ ParamIndex -- ^ 0-based Callable -- ^ deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) +data CallResolved = CallResolved + Call -- ^ + Resolved -- ^ + deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) + + -- | -- -- Usage: @@ -635,13 +787,9 @@ data Param = Param Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data Class = Class Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) -data CallResolved = CallResolved - Call -- ^ - Resolved -- ^ - deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) - data To = To Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data From = From Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) +data Func = Func Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data Method = Method Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data Callable = Callable Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data ConstStr = ConstStr Location deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) @@ -652,10 +800,13 @@ data Resolved = Resolved Fqn.Fqn deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data ArgIndex = ArgIndex Word deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data ParamIndex = ParamIndex Word deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) +data FuncName = FuncName String deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data MethodName = MethodName String deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data ConstStrValue = ConstStrValue String deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data SuperQualifiedName = SuperQualifiedName Fqn.Fqn deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) +data FuncDefinedInDir = FuncDefinedInDir FilePath deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) +data FuncDefinedInFile = FuncDefinedInFile FilePath deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data ClassDefinedInFile = ClassDefinedInFile FilePath deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) data SuperDefinedInFile = SuperDefinedInFile FilePath deriving ( Show, Eq, Ord, Generic, ToJSON, FromJSON ) @@ -674,7 +825,6 @@ data Fact = ClassDefCtor ClassDef | ParamNameCtor ParamName - | ArgForCallCtor ArgForCall | ArgiForCallCtor ArgiForCall | ConstStringCtor ConstString | DataflowEdgeCtor DataflowEdge @@ -704,7 +854,6 @@ prologify :: Fact -> String prologify (ParamNameCtor content) = prologify_ParamName content prologify (ClassDefCtor content) = prologify_ClassDef content -prologify (ArgForCallCtor content) = prologifyArgForCall content prologify (ArgiForCallCtor content) = prologifyArgiForCall content prologify (ConstStringCtor content) = prologify_ConstString content prologify (DataflowEdgeCtor content) = prologify_DataflowEdge content @@ -775,12 +924,6 @@ prologify_ConstBoolTrue :: ConstBoolTrue -> String prologify_ConstBoolTrue (ConstBoolTrue trueValue) = prologify_ConstBoolTrue' trueValue - -prologifyArgForCall' :: Location -> Location -> String -prologifyArgForCall' a c = printf "kb_arg_for_call( %s, %s )." (locationify a) (locationify c) - -prologifyArgForCall :: ArgForCall -> String -prologifyArgForCall (ArgForCall (Arg a) (Call c)) = prologifyArgForCall' a c prologify_MethodOfClass' :: Location -> Location -> String prologify_MethodOfClass' m c = printf "kb_method_of_class( %s, %s )." (locationify m) (locationify c)