A tool to map the access rights of network shares into BloodHound OpenGraphs.
Read the associated blog post: https://specterops.io/blog/2025/10/30/sharehound-an-opengraph-collector-for-network-shares/
This repository contains two implementations of ShareHound. They share the same goal — producing BloodHound OpenGraph JSON from SMB share permissions — but differ in language, runtime, and feature set. Pick whichever fits your workflow.
| Implementation | Path | Author | Best for |
|---|---|---|---|
| Python | Python/ |
Remi Gascou (@podalirius_) @ SpecterOps | The reference implementation; easy to extend and script |
| Go | Go/ |
Javier Azofra @ Siemens Healthineers | Large-scale scans (60,000+ hosts), checkpointing, static binaries |
Each subdirectory has its own README with full installation, usage, and configuration details:
- Map network shares of a domain and their rights in BloodHound OpenGraph format
- Highly customizable rule matching via the ShareQL language
- Multithreaded discovery of shares (Breadth First Search)
- NTLM, Kerberos, and pass-the-hash authentication
- CIDR range and target file support
- ZIP-compressed streaming output (handles millions of edges)
- Resumable scans via checkpoint files
--effective-access-onlymode to drastically reduce graph size on large environments- Cross-platform static builds (Linux, Windows, macOS)
Once you've imported the OpenGraph into BloodHound, these queries cover the most common needs. For more, see the per-implementation READMEs.
MATCH (p)-[r]->(s:NetworkShareSMB)
WHERE (p)-[:CanDelete]->(s)
AND (p)-[:CanDsControlAccess]->(s)
AND (p)-[:CanDsCreateChild]->(s)
AND (p)-[:CanDsDeleteChild]->(s)
AND (p)-[:CanDsDeleteTree]->(s)
AND (p)-[:CanDsListContents]->(s)
AND (p)-[:CanDsListObject]->(s)
AND (p)-[:CanDsReadProperty]->(s)
AND (p)-[:CanDsWriteExtendedProperties]->(s)
AND (p)-[:CanDsWriteProperty]->(s)
AND (p)-[:CanReadControl]->(s)
AND (p)-[:CanWriteDacl]->(s)
AND (p)-[:CanWriteOwner]->(s)
RETURN p,r,sMATCH x=(p)-[r:CanWriteDacl|CanWriteOwner|CanDsWriteProperty|CanDsWriteExtendedProperties]->(s:NetworkShareSMB)
RETURN xMATCH p=(h:NetworkShareHost)-[:HasNetworkShare]->(s:NetworkShareSMB)-[:Contains*0..]->(f:File)
WHERE toLower(f.name) = toLower("flag.txt")
RETURN pMATCH p=(h:NetworkShareHost)-[:HasNetworkShare]->(s:NetworkShareSMB)-[:Contains*0..]->(f:File)
WHERE toLower(f.extension) = toLower(".vmdk")
RETURN pCanEffectiveRead / CanEffectiveWrite / CanEffectiveExecute edges are emitted
by the Go implementation when the same SID has matching rights at both the share
and NTFS levels — i.e. the real access granted over SMB.
MATCH p=(principal)-[:CanEffectiveRead]->(f:File)
RETURN p- Original project: Remi Gascou (@podalirius_) @ SpecterOps — p0dalirius/ShareHound
- Go implementation: Javier Azofra @ Siemens Healthineers
- Associated blog post: ShareHound: An OpenGraph Collector for Network Shares
Pull requests are welcome for either implementation. Open an issue if you want to discuss a new feature first.