This commit is contained in:
Dmitry Zuikov 2024-09-20 07:29:36 +03:00
parent 627a3e0911
commit 4e96b1f7f1
4 changed files with 234 additions and 74 deletions

View File

@ -39,6 +39,7 @@ import Data.ByteString.Lazy.Char8 qualified as LBS8
import Data.ByteString qualified as BS
import Data.Either
import Data.Map qualified as Map
import Data.Set qualified as Set
import Data.Maybe
import Data.HashSet qualified as HS
import Data.HashMap.Strict (HashMap)
@ -592,6 +593,9 @@ refchanImport = do
here <- selectIsAlreadyScanned x
pure $ not here
fixmeGkSign <- putBlock sto "FIXMEGROUPKEYBLOCKv1" <&> fmap HashRef
>>= orThrowUser "hbs2 storage error. aborted"
walkRefChanTx @UNIX goodToGo chan $ \txh u -> do
case u of
@ -610,54 +614,42 @@ refchanImport = do
P orig (ProposeTran _ box) -> void $ runMaybeT do
(_, bs) <- unboxSignedBox0 box & toMPlus
AnnotatedHashRef _ href <- deserialiseOrFail @AnnotatedHashRef (LBS.fromStrict bs)
AnnotatedHashRef sn href <- deserialiseOrFail @AnnotatedHashRef (LBS.fromStrict bs)
& toMPlus . either (const Nothing) Just
scanned <- lift $ selectIsAlreadyScanned href
when (not scanned || ignCached) do
-- check if metadata tx
meta <- runExceptT (extractMetaData @'HBS2Basic (const $ pure Nothing) sto href)
<&> fromRight mempty
let parsed = parseTop meta & fromRight mempty
let isGk = not $ L.null [ True | ListVal [SymbolVal "GK:", _] <- parsed ]
debug $ "metadata:" <+> pretty isGk <+> pretty parsed
let isGk = sn == Just fixmeGkSign
if isGk then do
-- TODO: check-error-type
what <- liftIO (runExceptT $ getTreeContents sto href)
<&> either (const Nothing) Just
>>= toMPlus
gkz <- deserialiseOrFail @[GroupKey 'Symm 'HBS2Basic] what
& toMPlus
for_ gkz $ \gk -> do
atomically $ writeTQueue tq (Left (txh, orig, href, gk))
atomically $ writeTQueue tq (Left (txh, orig, href, href))
else do
what <- liftIO (runExceptT $ getTreeContents sto href)
<&> either (const Nothing) Just
>>= toMPlus
exported <- deserialiseOrFail @[FixmeExported] what
& toMPlus
let exported = deserialiseOrFail @[FixmeExported] what
& either (const Nothing) Just
for_ exported $ \e -> do
atomically $ writeTQueue tq (Right (txh, orig, href, e))
case exported of
Just e -> do
for_ e $ \x -> do
atomically $ writeTQueue tq (Right (txh, orig, href, x))
Nothing -> do
lift $ withState $ insertScanned txh
imported <- atomically $ flushTQueue tq
withState $ transactional do
for_ imported $ \case
Left (txh, orig, href, gk) -> do
hx <- writeAsMerkle sto (serialise gk)
notice $ "import GK" <+> pretty hx <+> "from" <+> pretty href
-- hx <- writeAsMerkle sto (serialise gk)
-- notice $ "import GK" <+> pretty hx <+> "from" <+> pretty href
-- let tx = AnnotatedHashRef _ href <- deserialiseOrFail @AnnotatedHashRef (LBS.fromStrict bs)
-- & toMPlus . either (const Nothing) Just
insertScanned txh
@ -844,7 +836,6 @@ fixmeRefChanInit = do
notice $ green "refchan added" <+> pretty (AsBase58 refchan)
refchanExportGroupKeys :: FixmePerks m => FixmeM m ()
refchanExportGroupKeys = do
@ -868,6 +859,8 @@ refchanExportGroupKeys = do
skip <- newTVarIO HS.empty
gkz <- newTVarIO HS.empty
fixmeSign <- putBlock sto "FIXMEGROUPKEYBLOCKv1" <&> fmap HashRef
walkRefChanTx @UNIX goodToGo chan $ \txh u -> do
case u of
@ -922,9 +915,16 @@ refchanExportGroupKeys = do
let (pk,sk) = (view peerSignPk creds, view peerSignSk creds)
keyz <- Map.fromList <$> S.toList_ do
keyz <- Set.fromList <$> S.toList_ do
for_ r $ \gkh -> void $ runMaybeT do
debug $ red $ "FOR GK" <+> pretty gkh
gk <- loadGroupKeyMaybe @'HBS2Basic sto gkh >>= toMPlus
-- the original groupkey should be indexed as well
lift $ S.yield gkh
gks <- liftIO (runKeymanClientRO $ findMatchedGroupKeySecret sto gk)
when (isNothing gks) do
@ -934,30 +934,69 @@ refchanExportGroupKeys = do
gk1 <- generateGroupKey @'HBS2Basic gks (HS.toList $ view refChanHeadReaders rch)
let lbs = serialise gk1
-- gkh1 <- writeAsMerkle sto lbs <&> HashRef
gkh1 <- writeAsMerkle sto lbs <&> HashRef
debug $ red "prepare new gk0" <+> pretty (LBS.length lbs) <+> pretty gkh <+> pretty (groupKeyId gk)
lift $ S.yield (groupKeyId gk, gk1)
lift $ S.yield gkh1
notice $ yellow $ "new gk:" <+> pretty (Map.size keyz)
notice $ yellow $ "new gk:" <+> pretty (Set.size keyz)
let nitems = 262144 `div` (125 * HS.size (view refChanHeadReaders rch) )
let chunks = Map.elems keyz & chunksOf nitems
-- let nitems = 262144 `div` (125 * HS.size (view refChanHeadReaders rch) )
-- let chunks = Map.elems keyz & chunksOf nitems
for_ chunks $ \x -> do
-- TODO: gk:performance-vs-reliability
-- ситуация такова: групповой ключ это меркл-дерево
-- для одного и того же блоба могут быть разные меркл-деревья,
-- так как могут быть разные настройки.
--
-- если распространять ключи по-одному, то хотя бы тот же ключ,
-- который мы создали изначально -- будет доступен по своему хэшу,
-- как отдельный артефакт.
--
-- Если писать их пачками, где каждый ключ представлен непосредственно,
-- то на принимающей стороне нет гарантии, что меркл дерево будет писаться
-- с таким же параметрами, хотя и может.
--
-- Решение: делать групповой ключ БЛОКОМ. тогда его размер будет ограничен,
-- но он хотя бы будет всегда однозначно определён хэшем.
--
-- Решение: ссылаться не на групповой ключ, а на хэш его секрета
-- что ломает текущую схему и обратная совместимость будет морокой.
--
-- Решение: добавить в hbs2-keyman возможно индексации единичного
-- ключа, и индексировать таким образом *исходные* ключи.
--
-- Тогда можно эти вот ключи писать пачками, их хэши не имеют особого значения,
-- если мы проиндексируем оригинальный ключ и будем знать, на какой секрет он
-- ссылается.
--
-- Заметим, что в один блок поместится аж >2000 читателей, что должно быть
-- более, чем достаточно => при таких группах вероятность утечки секрета
-- стремится к 1.0, так как большинство клало болт на меры безопасности.
--
-- Кстати говоря, проблема недостаточного количества авторов в ключе легко
-- решается полем ORIGIN, т.к мы можем эти самые ключи разделять.
--
-- Что бы не стоять перед такой проблемой, мы всегда можем распостранять эти ключи
-- по-одному, ЛИБО добавить в производный ключ поле
-- ORIGIN: где будет хэш изначального ключа.
--
-- Это нормально, так как мы сможем проверить, что у этих ключей
-- (текущий и ORIGIN) одинаковые хэши секретов.
--
-- Это всё равно оставляет возможность еще одной DoS атаки на сервис,
-- с распространением кривых ключей, но это хотя бы выяснимо, ну и атака
-- может быть только в рамках рефчана, т.е лечится выкидыванием пиров /
-- исключением зловредных авторов.
let gktreemeta = HM.fromList [ ("GK", Text.pack (show $ pretty $ L.length x)) ]
-- group keys are public (and already encrypted)
-- therefore, no encryption
href <- liftIO $ createTreeWithMetadata sto mzero gktreemeta (serialise x)
>>= orThrowPassIO
for_ (Set.toList keyz) $ \href -> do
let tx = AnnotatedHashRef Nothing href
let tx = AnnotatedHashRef fixmeSign href
let lbs = serialise tx
let box = makeSignedBox @'HBS2Basic @BS.ByteString pk sk (LBS.toStrict lbs)
warn $ "POST GK TX" <+> pretty (length x) <+> "tree" <+> pretty href
warn $ "post gk tx" <+> "tree" <+> pretty href
result <- callRpcWaitMay @RpcRefChanPropose (TimeoutSec 1) api (chan, box)

View File

@ -182,10 +182,7 @@ updateKeys = do
let gkz1 = deserialiseOrFail @(GroupKey 'Symm HBS2Basic) gkbs
& either mempty List.singleton
let gkz2 = deserialiseOrFail @[GroupKey 'Symm HBS2Basic] gkbs
& fromRight mempty
for_ (gkz1 <> gkz2) $ \gk -> do
for_ gkz1 $ \gk -> do
gkId <- getGroupKeyId gk & toMPlus

View File

@ -9,15 +9,16 @@
]
},
"locked": {
"lastModified": 1708680396,
"narHash": "sha256-ZPwDreNdnyCS/hNdaE0OqVhytm+SzZGRfGRTRvBuSzE=",
"ref": "refs/heads/master",
"rev": "221fde04a00a9c38d2f6c0d05b1e1c3457d5a827",
"revCount": 7,
"lastModified": 1713359411,
"narHash": "sha256-BzOZ6xU+Li5nIe71Wy4p+lOEQlYK/e94T0gBcP8IKgE=",
"ref": "generic-sql",
"rev": "03635c54b2e2bd809ec1196bc9082447279f6f24",
"revCount": 9,
"type": "git",
"url": "https://git.hbs2.net/5xrwbTzzweS9yeJQnrrUY9gQJfhJf84pbyHhF2MMmSft"
},
"original": {
"ref": "generic-sql",
"type": "git",
"url": "https://git.hbs2.net/5xrwbTzzweS9yeJQnrrUY9gQJfhJf84pbyHhF2MMmSft"
}
@ -82,6 +83,21 @@
"type": "github"
}
},
"flake-utils_10": {
"locked": {
"lastModified": 1644229661,
"narHash": "sha256-1YdnJAsNy69bpcjuoKdOYQX0YxZBiCYZo4Twxerqv7k=",
"owner": "numtide",
"repo": "flake-utils",
"rev": "3cecb5b042f7f209c56ffd8371b2711a290ec797",
"type": "github"
},
"original": {
"owner": "numtide",
"repo": "flake-utils",
"type": "github"
}
},
"flake-utils_2": {
"locked": {
"lastModified": 1644229661,
@ -187,6 +203,62 @@
"type": "github"
}
},
"flake-utils_9": {
"locked": {
"lastModified": 1644229661,
"narHash": "sha256-1YdnJAsNy69bpcjuoKdOYQX0YxZBiCYZo4Twxerqv7k=",
"owner": "numtide",
"repo": "flake-utils",
"rev": "3cecb5b042f7f209c56ffd8371b2711a290ec797",
"type": "github"
},
"original": {
"owner": "numtide",
"repo": "flake-utils",
"type": "github"
}
},
"fuzzy": {
"inputs": {
"haskell-flake-utils": "haskell-flake-utils_4",
"nixpkgs": [
"hbs2",
"nixpkgs"
]
},
"locked": {
"lastModified": 1715919110,
"narHash": "sha256-moioa3ixAZb0y/xxyxUVjSvXoSiDGXy/vAx6B70d2yM=",
"ref": "refs/heads/master",
"rev": "5a55c22750589b357e50b759d2a754df058446d6",
"revCount": 40,
"type": "git",
"url": "https://git.hbs2.net/GmcLB9gEPT4tbx9eyQiECwsu8oPyEh6qKEpQDtyBWVPA"
},
"original": {
"type": "git",
"url": "https://git.hbs2.net/GmcLB9gEPT4tbx9eyQiECwsu8oPyEh6qKEpQDtyBWVPA"
}
},
"fuzzy_2": {
"inputs": {
"haskell-flake-utils": "haskell-flake-utils_8",
"nixpkgs": "nixpkgs_2"
},
"locked": {
"lastModified": 1715918584,
"narHash": "sha256-moioa3ixAZb0y/xxyxUVjSvXoSiDGXy/vAx6B70d2yM=",
"rev": "831879978213a1aed15ac70aa116c33bcbe964b8",
"revCount": 63,
"type": "git",
"url": "http://git.hbs2.net/GmcLB9gEPT4tbx9eyQiECwsu8oPyEh6qKEpQDtyBWVPA?tag=0.1.3.1"
},
"original": {
"rev": "831879978213a1aed15ac70aa116c33bcbe964b8",
"type": "git",
"url": "http://git.hbs2.net/GmcLB9gEPT4tbx9eyQiECwsu8oPyEh6qKEpQDtyBWVPA?tag=0.1.3.1"
}
},
"haskell-flake-utils": {
"inputs": {
"flake-utils": "flake-utils_2"
@ -245,6 +317,24 @@
"inputs": {
"flake-utils": "flake-utils_5"
},
"locked": {
"lastModified": 1707809372,
"narHash": "sha256-wfTL9PlCSOqSSyU4eenFFI7pHrV21gba4GEILnI4nAU=",
"owner": "ivanovs-4",
"repo": "haskell-flake-utils",
"rev": "3cbdc5d6093e8b4464ae64097e0c8c61e4414ff2",
"type": "github"
},
"original": {
"owner": "ivanovs-4",
"repo": "haskell-flake-utils",
"type": "github"
}
},
"haskell-flake-utils_5": {
"inputs": {
"flake-utils": "flake-utils_6"
},
"locked": {
"lastModified": 1698938553,
"narHash": "sha256-oXpTKXioqFbl2mhhvpJIAvgNd+wYyv4ekI+YnJHEJ6s=",
@ -260,9 +350,9 @@
"type": "github"
}
},
"haskell-flake-utils_5": {
"haskell-flake-utils_6": {
"inputs": {
"flake-utils": "flake-utils_6"
"flake-utils": "flake-utils_7"
},
"locked": {
"lastModified": 1672412555,
@ -279,9 +369,9 @@
"type": "github"
}
},
"haskell-flake-utils_6": {
"haskell-flake-utils_7": {
"inputs": {
"flake-utils": "flake-utils_7"
"flake-utils": "flake-utils_8"
},
"locked": {
"lastModified": 1698938553,
@ -297,9 +387,27 @@
"type": "github"
}
},
"haskell-flake-utils_7": {
"haskell-flake-utils_8": {
"inputs": {
"flake-utils": "flake-utils_8"
"flake-utils": "flake-utils_9"
},
"locked": {
"lastModified": 1707809372,
"narHash": "sha256-wfTL9PlCSOqSSyU4eenFFI7pHrV21gba4GEILnI4nAU=",
"owner": "ivanovs-4",
"repo": "haskell-flake-utils",
"rev": "3cbdc5d6093e8b4464ae64097e0c8c61e4414ff2",
"type": "github"
},
"original": {
"owner": "ivanovs-4",
"repo": "haskell-flake-utils",
"type": "github"
}
},
"haskell-flake-utils_9": {
"inputs": {
"flake-utils": "flake-utils_10"
},
"locked": {
"lastModified": 1672412555,
@ -319,7 +427,8 @@
"inputs": {
"db-pipe": "db-pipe",
"fixme": "fixme",
"haskell-flake-utils": "haskell-flake-utils_4",
"fuzzy": "fuzzy",
"haskell-flake-utils": "haskell-flake-utils_5",
"hspup": "hspup",
"lsm": "lsm",
"nixpkgs": [
@ -329,17 +438,15 @@
"suckless-conf": "suckless-conf_2"
},
"locked": {
"lastModified": 1713159635,
"narHash": "sha256-iXf8qcJxePLM65E0fsAK2kj69/YIyQdNMrZ5yULzVGc=",
"ref": "hbs2-git-index",
"rev": "2289845078ba839bade83a1daf5234435e6e631e",
"revCount": 997,
"lastModified": 1726739166,
"narHash": "sha256-8IXnyZnKZY2kaKNgdYHDzDcMOxxmtSvkQ9HRctSM4xk=",
"rev": "627a3e0911d470b0f06d986d8bc663f934269d0e",
"revCount": 1022,
"type": "git",
"url": "http://git.hbs2/BTThPdHKF8XnEq4m6wzbKHKA6geLFK4ydYhBXAqBdHSP"
},
"original": {
"ref": "hbs2-git-index",
"rev": "2289845078ba839bade83a1daf5234435e6e631e",
"rev": "627a3e0911d470b0f06d986d8bc663f934269d0e",
"type": "git",
"url": "http://git.hbs2/BTThPdHKF8XnEq4m6wzbKHKA6geLFK4ydYhBXAqBdHSP"
}
@ -366,7 +473,7 @@
},
"hspup": {
"inputs": {
"haskell-flake-utils": "haskell-flake-utils_5",
"haskell-flake-utils": "haskell-flake-utils_6",
"nixpkgs": [
"hbs2",
"nixpkgs"
@ -388,7 +495,7 @@
},
"lsm": {
"inputs": {
"haskell-flake-utils": "haskell-flake-utils_6",
"haskell-flake-utils": "haskell-flake-utils_7",
"nixpkgs": [
"hbs2",
"nixpkgs"
@ -425,6 +532,22 @@
}
},
"nixpkgs_2": {
"locked": {
"lastModified": 1707451808,
"narHash": "sha256-UwDBUNHNRsYKFJzyTMVMTF5qS4xeJlWoeyJf+6vvamU=",
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "442d407992384ed9c0e6d352de75b69079904e4e",
"type": "github"
},
"original": {
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "442d407992384ed9c0e6d352de75b69079904e4e",
"type": "github"
}
},
"nixpkgs_3": {
"locked": {
"lastModified": 1709200309,
"narHash": "sha256-lKdtMbhnBNU1lr978T+wEYet3sfIXXgyiDZNEgx8CV8=",
@ -445,7 +568,7 @@
"extra-container": "extra-container",
"hbs2": "hbs2",
"home-manager": "home-manager",
"nixpkgs": "nixpkgs_2"
"nixpkgs": "nixpkgs_3"
}
},
"saltine": {
@ -490,22 +613,23 @@
},
"suckless-conf_2": {
"inputs": {
"haskell-flake-utils": "haskell-flake-utils_7",
"fuzzy": "fuzzy_2",
"haskell-flake-utils": "haskell-flake-utils_9",
"nixpkgs": [
"hbs2",
"nixpkgs"
]
},
"locked": {
"lastModified": 1704001322,
"narHash": "sha256-D7T/8wAg5J4KkRw0uB90w3+adY11aQaX7rjmQPXkkQc=",
"ref": "refs/heads/master",
"rev": "8cfc1272bb79ef6ad62ae6a625f21e239916d196",
"revCount": 28,
"lastModified": 1724740155,
"narHash": "sha256-dHAWLoQ0uZ2FckV/93qbXo6aYCTY+jARXiiTgUt6fcA=",
"rev": "b6c5087312e6c09e5c27082da47846f377f73756",
"revCount": 38,
"type": "git",
"url": "https://git.hbs2.net/JAuk1UJzZfbDGKVazSQU5yYQ3NGfk4gVeZzBCduf5TgQ"
},
"original": {
"rev": "b6c5087312e6c09e5c27082da47846f377f73756",
"type": "git",
"url": "https://git.hbs2.net/JAuk1UJzZfbDGKVazSQU5yYQ3NGfk4gVeZzBCduf5TgQ"
}

View File

@ -7,7 +7,7 @@
extra-container.url = "github:erikarvstedt/extra-container";
nixpkgs.url = "github:nixos/nixpkgs/nixpkgs-unstable";
hbs2.url =
"git+http://git.hbs2/BTThPdHKF8XnEq4m6wzbKHKA6geLFK4ydYhBXAqBdHSP?rev=3b8f3d48f486043c7fa2df5990e5ab96b71996e1";
"git+http://git.hbs2/BTThPdHKF8XnEq4m6wzbKHKA6geLFK4ydYhBXAqBdHSP?rev=627a3e0911d470b0f06d986d8bc663f934269d0e";
hbs2.inputs.nixpkgs.follows = "nixpkgs";
home-manager.url = "github:nix-community/home-manager";