Access control (BorgAuth)
BorgAuth numeric authority levels and who can call what
Every access check in the protocol runs through BorgAuth, one ACL contract per cyberCORP. BorgAuth uses numeric role levels in a hierarchy instead of named roles.
Source:
src/libs/auth.sol
The role model
A role is a uint256, and higher numbers outrank lower ones. onlyRole(role) passes when userRoles[user] >= role. It is a threshold check; matchRole is the exact-match variant.
Built-in role constants
OWNER_ROLE
99
ADMIN_ROLE
98
PRIVILEGED_ROLE
97
Roles the protocol assigns
The CyberCorpFactory and CyberCorp set these levels when a cyberCORP is deployed:
Company officer (CompanyOfficer.eoa)
200
Set by CyberCorp.addOfficer / updateOfficer and by the factory, never lowering a higher custom level; removal zeroes only an exact 200. 200 ≥ 99, so officers also pass onlyOwner.
CyberCorp contract
200
So the corp can act on its own auth.
IssuanceManager, DealManager, RoundManager
99 (OWNER_ROLE)
So the manager contracts can call owner-gated functions on the suite.
The deploying factory (CyberCorpFactory, or the specialised factory used)
99 (OWNER_ROLE)
The BorgAuth constructor makes its deployer the owner, and the factory does not renounce the level after deployment.
The factory's level is a standing owner grant from the company to a contract MetaLeX can upgrade. Some companies, v5 companies among them, still grant it, and others do not. Check userRoles(<factory address>) on your company's BorgAuth; an owner can remove the grant with updateRole(factory, 0).
Authority is the numeric level a function requires. BorgAuth defines no named roles such as ISSUER_AUTHORITY or OFFICER_AUTHORITY, and 200 is the level a human officer holds.
BorgAuth functions
updateRoleis the single grant and revoke entry point. It sets a user's level up or down and requiresOWNER_ROLE.zeroOwnerrenounces the owner's own level to0, permanently removing its admin control from contracts using this auth.Role adapters.
setRoleAdapterplugs in anIAuthAdapter, so custom logic (a credential check, for example) can satisfy a role instead of, or as well as, a stored level.Ownership transfer takes two steps:
initTransferOwnership, thenacceptOwnership.
Using BorgAuth in a contract: BorgAuthACL
Protocol contracts inherit BorgAuthACL, which holds the AUTH reference and provides modifiers:
onlyOwner
≥ OWNER_ROLE (99)
onlyAdmin
≥ ADMIN_ROLE (98)
onlyPriv
≥ PRIVILEGED_ROLE (97)
onlyRole(n)
≥ n
matchRole(n)
exactly n
Example: CyberCorp.addEscrowedOfficerSignature is onlyRole(200), so only an officer (level 200) can call it; most other CyberCorp functions are onlyOwner (level 99 or above).
onlyIssuanceManager and the token contracts
onlyIssuanceManager checks that msg.sender is the IssuanceManager contract; it is not a BorgAuth role check. End users act through the IssuanceManager, which BorgAuth authorizes. CyberShares gates its mint, burn and configuration functions this way.
CyberScrip has two surfaces:
Strictly
onlyIssuanceManager:mint,burnFromandforceBurn. Force burn also moves vault backing, so admins useIssuanceManager.forceScripBurn.onlyIssuanceManagerOrAdmin:setRestrictionHook,setFrozen,forceTransfer,setMaxHolderCountand the three one-waydisable*switches, callable directly by a BorgAuthADMIN_ROLE(98) holder. On v4 scrip,setMaxHolderCountisonlyIssuanceManagerand the v4 IssuanceManager has no wrapper for it, so a v4 company cannot set a holder cap.
LedgerEntryToken, the LET contract, also has two surfaces:
Strictly
onlyIssuanceManager: minting and assignment (safeMint, bothsafeMintAndAssignoverloads,safeMintFromAndAssign,assignCert),updateCertificateDetails,setExtensionandupdateIssuanceManager.onlyIssuanceManagerOrAdmin: the administrative surface, callable directly on the LET contract by a BorgAuthADMIN_ROLE(98) holder (the modifier resolves the IssuanceManager'sAUTH()and checks the role): restriction hooks, the delivery and registration transferability switches, default and per-LET legends,voidCert/unvoidCert,addIssuerSignatureandendorseCertificate, issue and acquisition timestamps (and the tacking anchor), reserved units,setSeriesData, the look-through badge, andinitializeHolderCount.
Last updated
Was this helpful?
