183 lines
6.3 KiB
Dart
183 lines
6.3 KiB
Dart
///
|
|
/// CCC provider specification models.
|
|
///
|
|
|
|
import 'package:letusmsg/ccc/cipher_constants.dart';
|
|
|
|
/// Execution strategy for provider routing inside CCC.
|
|
enum CccExecutionMode {
|
|
strict,
|
|
efficient,
|
|
auto,
|
|
}
|
|
|
|
CccExecutionMode cccExecutionModeFromString(String raw) {
|
|
switch (raw.trim().toLowerCase()) {
|
|
case 'strict':
|
|
return CccExecutionMode.strict;
|
|
case 'efficient':
|
|
return CccExecutionMode.efficient;
|
|
case 'auto':
|
|
return CccExecutionMode.auto;
|
|
default:
|
|
throw ArgumentError('Unsupported CCC execution mode: $raw');
|
|
}
|
|
}
|
|
|
|
/// Logical provider identities used by CCC channel profiles.
|
|
enum CccCryptoProvider {
|
|
cryptography,
|
|
wolfssl,
|
|
openssl,
|
|
boringssl,
|
|
}
|
|
|
|
/// Provider entry in a CCC provider chain.
|
|
///
|
|
/// Each provider advertises the ciphers it contributes to the channel plan.
|
|
class CccProviderSpec {
|
|
final CccCryptoProvider provider;
|
|
final List<int> ciphers;
|
|
|
|
const CccProviderSpec({
|
|
required this.provider,
|
|
required this.ciphers,
|
|
});
|
|
|
|
Map<String, dynamic> toMap() {
|
|
return {
|
|
'provider': provider.name,
|
|
'ciphers': ciphers,
|
|
};
|
|
}
|
|
}
|
|
|
|
/// Per-provider, per-cipher capability metadata.
|
|
class CccCipherCapability {
|
|
/// Whether the provider is currently available in this codebase/runtime.
|
|
///
|
|
/// `true` means the provider can be selected as primary in `auto` mode.
|
|
/// `false` means it can still appear in route planning metadata but should
|
|
/// not be chosen as active primary until availability changes.
|
|
final bool available;
|
|
|
|
/// Whether input/output format is identical across providers for this cipher.
|
|
///
|
|
/// This guards fallback safety. If this is `false`, fallback should be
|
|
/// treated as incompatible for that cipher unless a migration adapter exists.
|
|
final bool deterministicIo;
|
|
|
|
/// Relative efficiency score from 0..100 (higher = faster/cheaper).
|
|
///
|
|
/// Used by `efficient` mode to rank candidate providers for a cipher.
|
|
final int efficiencyScore;
|
|
|
|
/// Relative reliability score from 0..100 (higher = more trusted/stable).
|
|
///
|
|
/// Used as tie-breaker when efficiency scores are equal.
|
|
final int reliabilityScore;
|
|
|
|
/// Creates immutable provider capability metadata used by CCC route planning.
|
|
///
|
|
/// Parameter meanings:
|
|
/// - [available]: runtime/provider readiness flag.
|
|
/// - [deterministicIo]: indicates safe cross-provider fallback compatibility.
|
|
/// - [efficiencyScore]: performance rank (0..100), higher is better.
|
|
/// - [reliabilityScore]: confidence rank (0..100), higher is better.
|
|
const CccCipherCapability({
|
|
required this.available,
|
|
required this.deterministicIo,
|
|
required this.efficiencyScore,
|
|
required this.reliabilityScore,
|
|
});
|
|
}
|
|
|
|
/// Runtime/provider capability registry used by CCC route planning.
|
|
class CccProviderCatalog {
|
|
/// Placeholder score used until benchmark pipeline is implemented.
|
|
///
|
|
/// TODO(j3g): Replace with measured values from automated perf/reliability
|
|
/// benchmark suite per provider/cipher.
|
|
///
|
|
/// Example efficiency calculation (normalized 0..100):
|
|
/// efficiency = normalize(throughputMBps / latencyMs)
|
|
///
|
|
/// Example reliability calculation (normalized 0..100):
|
|
/// reliability = normalize((1 - errorRate) * 100 - crashPenalty - cvePenalty)
|
|
static const int pendingEfficiencyScore = 50;
|
|
static const int pendingReliabilityScore = 50;
|
|
|
|
static const CccCipherCapability _availableDeterministicPending = CccCipherCapability(
|
|
available: true,
|
|
deterministicIo: true,
|
|
efficiencyScore: pendingEfficiencyScore,
|
|
reliabilityScore: pendingReliabilityScore,
|
|
);
|
|
|
|
static const CccCipherCapability _unavailableDeterministicPending = CccCipherCapability(
|
|
available: false,
|
|
deterministicIo: true,
|
|
efficiencyScore: pendingEfficiencyScore,
|
|
reliabilityScore: pendingReliabilityScore,
|
|
);
|
|
|
|
static const Map<CccCryptoProvider, Map<int, CccCipherCapability>> capabilities = {
|
|
CccCryptoProvider.cryptography: {
|
|
CipherConstants.AES_GCM_256: _availableDeterministicPending,
|
|
CipherConstants.CHACHA20_POLY1305: _availableDeterministicPending,
|
|
CipherConstants.XCHACHA20_POLY1305: _availableDeterministicPending,
|
|
CipherConstants.HMAC_SHA512: _availableDeterministicPending,
|
|
CipherConstants.BLAKE2B: _availableDeterministicPending,
|
|
},
|
|
CccCryptoProvider.wolfssl: {
|
|
CipherConstants.AES_GCM_256: _unavailableDeterministicPending,
|
|
CipherConstants.CHACHA20_POLY1305: _unavailableDeterministicPending,
|
|
CipherConstants.XCHACHA20_POLY1305: _unavailableDeterministicPending,
|
|
CipherConstants.HMAC_SHA512: _unavailableDeterministicPending,
|
|
CipherConstants.BLAKE2B: _unavailableDeterministicPending,
|
|
},
|
|
CccCryptoProvider.openssl: {
|
|
CipherConstants.AES_GCM_256: _unavailableDeterministicPending,
|
|
CipherConstants.CHACHA20_POLY1305: _unavailableDeterministicPending,
|
|
CipherConstants.HMAC_SHA512: _unavailableDeterministicPending,
|
|
CipherConstants.BLAKE2B: _unavailableDeterministicPending,
|
|
},
|
|
CccCryptoProvider.boringssl: {
|
|
CipherConstants.AES_GCM_256: _unavailableDeterministicPending,
|
|
CipherConstants.CHACHA20_POLY1305: _unavailableDeterministicPending,
|
|
CipherConstants.XCHACHA20_POLY1305: _unavailableDeterministicPending,
|
|
CipherConstants.HMAC_SHA512: _unavailableDeterministicPending,
|
|
CipherConstants.BLAKE2B: _unavailableDeterministicPending,
|
|
},
|
|
};
|
|
|
|
static CccCipherCapability? capability(CccCryptoProvider provider, int cipher) {
|
|
return capabilities[provider]?[cipher];
|
|
}
|
|
|
|
static bool supports(CccCryptoProvider provider, int cipher) {
|
|
return capability(provider, cipher) != null;
|
|
}
|
|
|
|
static List<CccCryptoProvider> providersSupporting(
|
|
int cipher, {
|
|
bool availableOnly = true,
|
|
}) {
|
|
final ranked = <({CccCryptoProvider provider, CccCipherCapability capability})>[];
|
|
for (final entry in capabilities.entries) {
|
|
final cap = entry.value[cipher];
|
|
if (cap == null) continue;
|
|
if (availableOnly && !cap.available) continue;
|
|
ranked.add((provider: entry.key, capability: cap));
|
|
}
|
|
|
|
ranked.sort((a, b) {
|
|
final perf = b.capability.efficiencyScore.compareTo(a.capability.efficiencyScore);
|
|
if (perf != 0) return perf;
|
|
return b.capability.reliabilityScore.compareTo(a.capability.reliabilityScore);
|
|
});
|
|
|
|
return ranked.map((item) => item.provider).toList(growable: false);
|
|
}
|
|
}
|