chore: disable CI build job and tidy dependencies

- Comment out the build job in GitHub Actions CI workflow to prevent automated compilation - Remove version and default image from docker-compose.yml - Clean up unused indirect dependencies in go.sum for a leaner module

lemon-mint committed Oct 27, 2025 at 00:00 UTC 09a14e2c796f6ef5bdc5de81cae28aedad2334ad
49 files changed +10608 -4128
.github/workflows/ci.yml
+36 -36
@@ -66,42 +66,42 @@ jobs:
66 exit 1
67 fi
68
69 - # Build job - verify binaries compile
70 - build:
71 - name: Build
72 - runs-on: ubuntu-latest
73 - strategy:
74 - matrix:
75 - go-version: ['1.25.0']
76 - steps:
77 - - name: Checkout code
78 - uses: actions/checkout@v4
79 -
80 - - name: Set up Go ${{ matrix.go-version }}
81 - uses: actions/setup-go@v5
82 - with:
83 - go-version: ${{ matrix.go-version }}
84 - cache: true
85 -
86 - - name: Download dependencies
87 - run: go mod download
88 -
89 - - name: Build server binary
90 - run: go build -v -trimpath -o bin/relaydns-server ./cmd/server
91 -
92 - - name: Build example HTTP client
93 - run: go build -v -trimpath -o bin/relaydns-client ./sdk/go/examples/http-client
94 -
95 - - name: Build example chat client
96 - run: go build -v -trimpath -o bin/relaydns-chat ./sdk/go/examples/chat
97 -
98 - - name: Upload binaries
99 - uses: actions/upload-artifact@v4
100 - if: matrix.go-version == '1.25.0'
101 - with:
102 - name: binaries
103 - path: bin/*
104 - retention-days: 7
69 +# # Build job - verify binaries compile
70 +# build:
71 +# name: Build
72 +# runs-on: ubuntu-latest
73 +# strategy:
74 +# matrix:
75 +# go-version: ['1.25.0']
76 +# steps:
77 +# - name: Checkout code
78 +# uses: actions/checkout@v4
79 +#
80 +# - name: Set up Go ${{ matrix.go-version }}
81 +# uses: actions/setup-go@v5
82 +# with:
83 +# go-version: ${{ matrix.go-version }}
84 +# cache: true
85 +#
86 +# - name: Download dependencies
87 +# run: go mod download
88 +#
89 +# - name: Build server binary
90 +# run: go build -v -trimpath -o bin/relaydns-server ./cmd/server
91 +#
92 +# - name: Build example HTTP client
93 +# run: go build -v -trimpath -o bin/relaydns-client ./sdk/go/examples/http-client
94 +#
95 +# - name: Build example chat client
96 +# run: go build -v -trimpath -o bin/relaydns-chat ./sdk/go/examples/chat
97 +#
98 +# - name: Upload binaries
99 +# uses: actions/upload-artifact@v4
100 +# if: matrix.go-version == '1.25.0'
101 +# with:
102 +# name: binaries
103 +# path: bin/*
104 +# retention-days: 7
105
106 # # Test job - unit tests with race detection
107 # test:
.pre-commit-config.yaml deleted
-83
@@ -1,83 +0,0 @@
1 -# Pre-commit hooks for Go project
2 -# Install: pip install pre-commit && pre-commit install
3 -# Run manually: pre-commit run --all-files
4 -# Update hooks: pre-commit autoupdate
5 -
6 -repos:
7 - # General file checks
8 - - repo: https://github.com/pre-commit/pre-commit-hooks
9 - rev: v6.0.0
10 - hooks:
11 - - id: trailing-whitespace
12 - args: [--markdown-linebreak-ext=md]
13 - - id: end-of-file-fixer
14 - - id: check-yaml
15 - args: [--allow-multiple-documents]
16 - - id: check-added-large-files
17 - args: [--maxkb=1024]
18 - - id: check-merge-conflict
19 - - id: check-case-conflict
20 - - id: mixed-line-ending
21 - args: [--fix=lf]
22 - - id: detect-private-key
23 -
24 - # YAML linting
25 - - repo: https://github.com/adrienverge/yamllint
26 - rev: v1.37.1
27 - hooks:
28 - - id: yamllint
29 - args: [-c=.yamllint.yml]
30 - exclude: ^(vendor/|\.github/)
31 -
32 - # Local checks (formatting, go vet, mod tidy, build, test)
33 - - repo: local
34 - hooks:
35 - - id: golangci-lint-run
36 - name: golangci-lint run
37 - description: Run golangci-lint to analyze Go code
38 - entry: golangci-lint run
39 - language: system
40 - pass_filenames: false
41 - types: [go]
42 -
43 - - id: golangci-lint-fmt
44 - name: golangci-lint fmt
45 - description: Format Go code using golangci-lint
46 - entry: golangci-lint fmt
47 - language: system
48 - pass_filenames: false
49 - types: [go]
50 -
51 - - id: go-vet
52 - name: go vet
53 - description: Run 'go vet' to examine Go source code
54 - entry: go vet
55 - language: system
56 - pass_filenames: false
57 - types: [go]
58 - args: [./...]
59 -
60 - - id: go-mod-tidy
61 - name: go mod tidy
62 - description: Run 'go mod tidy' to ensure go.mod matches source
63 - entry: bash -c 'go mod tidy && git diff --exit-code go.mod go.sum'
64 - language: system
65 - pass_filenames: false
66 - always_run: true
67 -
68 - - id: go-build
69 - name: go build
70 - description: Build all Go binaries to ensure they compile
71 - entry: bash -c 'go build -trimpath -o /tmp/relaydns-server ./cmd/server && go build -trimpath -o /tmp/relaydns-client ./cmd/example_http_client && go build -trimpath -o /tmp/relaydns-chat ./cmd/example_chat'
72 - language: system
73 - pass_filenames: false
74 - types: [go]
75 -
76 - - id: go-test
77 - name: go test
78 - description: Run unit tests with race detector
79 - entry: go test
80 - language: system
81 - pass_filenames: false
82 - types: [go]
83 - args: [-v, -race, -timeout=3m, ./...]
.yamllint.yml deleted
-14
@@ -1,14 +0,0 @@
1 ----
2 -extends: default
3 -
4 -rules:
5 - line-length:
6 - max: 120
7 - level: warning
8 - indentation:
9 - spaces: 2
10 - document-start: disable
11 - truthy:
12 - allowed-values: ['true', 'false', 'on', 'off']
13 - comments:
14 - min-spaces-from-content: 1
CI_CD.md deleted
-475
@@ -1,475 +0,0 @@
1 -# CI/CD Setup Guide
2 -
3 -This document describes the CI/CD infrastructure for the RelayDNS project, including pre-commit hooks, linters, formatters, sanitizers, and GitHub Actions workflows.
4 -
5 -## Table of Contents
6 -
7 -- [Overview](#overview)
8 -- [Quick Start](#quick-start)
9 -- [Tools](#tools)
10 -- [Pre-commit Hooks](#pre-commit-hooks)
11 -- [GitHub Actions](#github-actions)
12 -- [Makefile Targets](#makefile-targets)
13 -- [Configuration Files](#configuration-files)
14 -- [Troubleshooting](#troubleshooting)
15 -
16 -## Overview
17 -
18 -The CI/CD setup includes:
19 -
20 -1. **Pre-commit hooks** - Run checks locally before commits
21 -2. **golangci-lint** - Comprehensive Go linting with 30+ linters
22 -3. **Formatters** - gofmt, goimports, gci
23 -4. **Sanitizers** - Race detector, staticcheck, gosec, govulncheck
24 -5. **GitHub Actions** - Automated CI pipeline on push/PR
25 -
26 -## Quick Start
27 -
28 -### 1. Install Required Tools
29 -
30 -```bash
31 -# Install Go tools
32 -make install-tools
33 -
34 -# Install golangci-lint
35 -# See: https://golangci-lint.run/usage/install/
36 -curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v2.5.0
37 -
38 -# Install pre-commit (Python required)
39 -pip install pre-commit
40 -
41 -# Install pre-commit hooks
42 -make pre-commit-install
43 -```
44 -
45 -### 2. Run Local CI Checks
46 -
47 -```bash
48 -# Run all local CI checks (fmt, tidy, vet, lint, test-race)
49 -make ci-local
50 -
51 -# Or run individual checks
52 -make fmt # Format code
53 -make lint # Run linters
54 -make test-race # Run tests with race detector
55 -```
56 -
57 -### 3. Commit Changes
58 -
59 -After installing pre-commit hooks, every commit will automatically run:
60 -- File checks (trailing whitespace, EOF, YAML validation)
61 -- Go formatting (gofmt, goimports)
62 -- Go vet
63 -- golangci-lint
64 -- Build check (ensure all binaries compile)
65 -- Tests with race detector
66 -
67 -```bash
68 -git add .
69 -git commit -m "Your commit message"
70 -# Pre-commit hooks will run automatically
71 -```
72 -
73 -## Tools
74 -
75 -### golangci-lint
76 -
77 -Configuration: `.golangci.yml`
78 -
79 -Enabled linters:
80 -- **Formatters**: gofmt, goimports, gci
81 -- **Core**: govet, staticcheck, errcheck, gosimple, ineffassign, unused
82 -- **Style**: revive, stylecheck
83 -- **Security**: gosec, bodyclose, noctx, rowserrcheck, sqlclosecheck
84 -- **Complexity**: gocyclo, gocognit, cyclop, nestif
85 -- **Error handling**: errname, errorlint
86 -- **Performance**: prealloc
87 -- **Code quality**: dupl, goconst, unconvert, unparam, nakedret, misspell
88 -
89 -Usage:
90 -```bash
91 -# Run all linters
92 -make lint
93 -
94 -# Run with auto-fix
95 -make lint-fix
96 -
97 -# Run golangci-lint directly
98 -golangci-lint run --timeout=5m --config=.golangci.yml
99 -```
100 -
101 -### Formatters
102 -
103 -**gofmt** - Standard Go formatter
104 -```bash
105 -go fmt ./...
106 -```
107 -
108 -**goimports** - Organizes imports
109 -```bash
110 -goimports -local github.com/gosuda/relaydns -w .
111 -```
112 -
113 -**gci** - Controls import order (integrated in golangci-lint)
114 -- Standard library imports
115 -- Third-party imports
116 -- Local imports (github.com/gosuda/relaydns)
117 -
118 -### Sanitizers
119 -
120 -**Race Detector** - Detects data races
121 -```bash
122 -make test-race
123 -go test -race ./...
124 -```
125 -
126 -**staticcheck** - Advanced static analysis
127 -```bash
128 -make staticcheck
129 -staticcheck ./...
130 -```
131 -
132 -**gosec** - Security scanner
133 -```bash
134 -make gosec
135 -gosec ./...
136 -```
137 -
138 -**govulncheck** - Vulnerability scanner
139 -```bash
140 -make govulncheck
141 -govulncheck ./...
142 -```
143 -
144 -## Pre-commit Hooks
145 -
146 -Configuration: `.pre-commit-config.yaml`
147 -
148 -Hooks run automatically before each commit:
149 -
150 -1. **General file checks**
151 - - Trailing whitespace
152 - - End of file fixer
153 - - YAML validation
154 - - Large file check (max 1MB)
155 - - Merge conflict detection
156 - - Private key detection
157 -
158 -2. **Go checks**
159 - - `go fmt ./...`
160 - - `goimports -local github.com/gosuda/relaydns`
161 - - `go vet ./...`
162 - - `go mod tidy` (ensures go.mod is clean)
163 - - `golangci-lint run`
164 -
165 -3. **Build verification**
166 - - Compile all binaries (server, client, chat)
167 -
168 -4. **Tests**
169 - - Run all tests with race detector
170 -
171 -5. **Additional linting**
172 - - YAML linting (yamllint)
173 - - Dockerfile linting (hadolint)
174 -
175 -### Managing Pre-commit Hooks
176 -
177 -```bash
178 -# Install hooks
179 -make pre-commit-install
180 -
181 -# Run manually on all files
182 -make pre-commit-run
183 -pre-commit run --all-files
184 -
185 -# Run manually on staged files
186 -pre-commit run
187 -
188 -# Update hooks to latest versions
189 -pre-commit autoupdate
190 -
191 -# Skip hooks for a commit (use sparingly)
192 -git commit --no-verify -m "Emergency fix"
193 -```
194 -
195 -## GitHub Actions
196 -
197 -Configuration: `.github/workflows/ci.yml`
198 -
199 -Triggered on:
200 -- Push to `main` or `develop` branches
201 -- Pull requests to `main` or `develop`
202 -- Manual workflow dispatch
203 -
204 -### Jobs
205 -
206 -#### 1. Lint Job
207 -- Runs on: `ubuntu-latest`
208 -- Go version: `1.25.0`
209 -- Steps:
210 - - Verify dependencies
211 - - Run gofmt check
212 - - Run goimports check
213 - - Run go vet
214 - - Run golangci-lint
215 - - Check go.mod tidiness
216 -
217 -#### 2. Build Job
218 -- Runs on: `ubuntu-latest`
219 -- Go versions: `1.25.0`, `1.24.x` (matrix)
220 -- Steps:
221 - - Build server binary
222 - - Build example HTTP client
223 - - Build example chat client
224 - - Upload binaries (artifacts, 7 days retention)
225 -
226 -#### 3. Test Job
227 -- Runs on: `ubuntu-latest`
228 -- Go versions: `1.25.0`, `1.24.x` (matrix)
229 -- Steps:
230 - - Run tests with race detector
231 - - Generate coverage report
232 - - Upload coverage HTML (7 days retention)
233 - - Check coverage threshold (warning if < 30%)
234 -
235 -#### 4. Sanitizers Job
236 -- Runs on: `ubuntu-latest`
237 -- Go version: `1.25.0`
238 -- Steps:
239 - - Run staticcheck
240 - - Run gosec (security scanner)
241 - - Upload gosec report (JSON)
242 - - Check for ineffective assignments
243 - - Check for unused code
244 -
245 -#### 5. Docker Job
246 -- Runs on: `ubuntu-latest`
247 -- Steps:
248 - - Build Docker image
249 - - Use buildx for caching
250 - - Validate Dockerfile
251 -
252 -#### 6. Dependencies Job
253 -- Runs on: `ubuntu-latest`
254 -- Go version: `1.25.0`
255 -- Steps:
256 - - Run govulncheck (vulnerability scanner)
257 - - Check for outdated dependencies
258 -
259 -### Viewing Results
260 -
261 -- Go to GitHub Actions tab in your repository
262 -- Click on a workflow run to see job details
263 -- Download artifacts (binaries, coverage reports) from workflow summary
264 -
265 -## Makefile Targets
266 -
267 -### Development
268 -
269 -```bash
270 -make fmt # Format Go code with gofmt and goimports
271 -make tidy # Tidy go.mod
272 -make vet # Run go vet
273 -```
274 -
275 -### Linting
276 -
277 -```bash
278 -make lint # Run golangci-lint
279 -make lint-fix # Run golangci-lint with auto-fix
280 -```
281 -
282 -### Testing
283 -
284 -```bash
285 -make test # Run unit tests
286 -make test-race # Run tests with race detector
287 -make test-coverage # Run tests with coverage report (generates coverage.html)
288 -```
289 -
290 -### Static Analysis & Security
291 -
292 -```bash
293 -make staticcheck # Run staticcheck
294 -make gosec # Run gosec security scanner
295 -make govulncheck # Check for known vulnerabilities
296 -```
297 -
298 -### Build
299 -
300 -```bash
301 -make build-all # Build all binaries (server, client, chat)
302 -make client-build # Build example HTTP client
303 -make chat-build # Build example chat client
304 -```
305 -
306 -### Pre-commit
307 -
308 -```bash
309 -make pre-commit-install # Install pre-commit hooks
310 -make pre-commit-run # Run pre-commit on all files
311 -```
312 -
313 -### CI/CD
314 -
315 -```bash
316 -make ci-local # Run local CI checks (fmt, tidy, vet, lint, test-race)
317 -make install-tools # Install development tools
318 -make clean # Remove build artifacts and reports
319 -```
320 -
321 -## Configuration Files
322 -
323 -### `.golangci.yml`
324 -
325 -Main linter configuration with 30+ linters enabled.
326 -
327 -Key settings:
328 -- Timeout: 5 minutes
329 -- Go version: 1.25
330 -- Local prefix: `github.com/gosuda/relaydns`
331 -- Excludes test files from certain linters
332 -- Excludes example code from security checks
333 -
334 -### `.pre-commit-config.yaml`
335 -
336 -Pre-commit hooks configuration.
337 -
338 -Repos:
339 -- `pre-commit/pre-commit-hooks`: General file checks
340 -- `dnephin/pre-commit-golang`: Go formatting and checks
341 -- `golangci/golangci-lint`: Comprehensive linting
342 -- `local`: Build and test checks
343 -- `adrienverge/yamllint`: YAML linting
344 -- `hadolint/hadolint`: Dockerfile linting
345 -
346 -### `.yamllint.yml`
347 -
348 -YAML linting configuration.
349 -
350 -Settings:
351 -- Max line length: 120 (warning level)
352 -- Indentation: 2 spaces
353 -- Document start: disabled
354 -- Truthy values: `true`, `false`, `on`, `off`
355 -
356 -### `.github/workflows/ci.yml`
357 -
358 -GitHub Actions workflow definition with 6 jobs:
359 -1. Lint
360 -2. Build
361 -3. Test
362 -4. Sanitizers
363 -5. Docker
364 -6. Dependencies
365 -
366 -## Troubleshooting
367 -
368 -### golangci-lint fails with "deadline exceeded"
369 -
370 -Increase timeout:
371 -```bash
372 -golangci-lint run --timeout=10m
373 -```
374 -
375 -Or edit `.golangci.yml`:
376 -```yaml
377 -run:
378 - timeout: 10m
379 -```
380 -
381 -### Pre-commit hooks are slow
382 -
383 -Skip build and test checks for faster commits:
384 -```bash
385 -SKIP=go-build,go-test git commit -m "Quick fix"
386 -```
387 -
388 -Or disable specific hooks in `.pre-commit-config.yaml`.
389 -
390 -### GitHub Actions fails on Go 1.24.x
391 -
392 -The project requires Go 1.25.0 features. Consider removing Go 1.24.x from the matrix if incompatible.
393 -
394 -Edit `.github/workflows/ci.yml`:
395 -```yaml
396 -strategy:
397 - matrix:
398 - go-version: ['1.25.0'] # Remove 1.24.x
399 -```
400 -
401 -### Pre-commit installation fails
402 -
403 -Ensure Python and pip are installed:
404 -```bash
405 -python3 --version
406 -pip --version
407 -pip install --user pre-commit
408 -```
409 -
410 -### golangci-lint not found
411 -
412 -Install golangci-lint:
413 -```bash
414 -# Linux/macOS
415 -curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v2.5.0
416 -
417 -# Or using Go
418 -go install github.com/golangci/golangci-lint/cmd/golangci-lint@v2.5.0
419 -
420 -# Verify installation
421 -golangci-lint --version
422 -```
423 -
424 -### Tests fail with race detector
425 -
426 -Race detector found a data race. Fix the race condition in your code:
427 -1. Review the race detector output
428 -2. Identify the conflicting goroutines
429 -3. Add proper synchronization (mutex, channel, atomic)
430 -4. Re-run tests
431 -
432 -### Coverage report not generated
433 -
434 -Ensure you have write permissions and run:
435 -```bash
436 -make test-coverage
437 -# Opens coverage.html in browser
438 -open coverage.html # macOS
439 -xdg-open coverage.html # Linux
440 -```
441 -
442 -## Best Practices
443 -
444 -1. **Always run `make ci-local` before pushing**
445 - - Catches issues early
446 - - Reduces CI failures
447 -
448 -2. **Fix linter warnings**
449 - - Don't disable linters without good reason
450 - - Use `//nolint:lintername` sparingly with explanation
451 -
452 -3. **Maintain test coverage**
453 - - Aim for > 50% coverage
454 - - Write tests for critical paths
455 - - Use table-driven tests
456 -
457 -4. **Keep dependencies updated**
458 - - Run `make govulncheck` regularly
459 - - Update vulnerable dependencies promptly
460 -
461 -5. **Use pre-commit hooks**
462 - - Prevents committing broken code
463 - - Enforces code quality standards
464 -
465 -6. **Review GitHub Actions failures**
466 - - Don't merge PRs with failing checks
467 - - Investigate root causes, don't just re-run
468 -
469 -## Additional Resources
470 -
471 -- [golangci-lint documentation](https://golangci-lint.run/)
472 -- [pre-commit documentation](https://pre-commit.com/)
473 -- [GitHub Actions documentation](https://docs.github.com/en/actions)
474 -- [Go race detector](https://go.dev/doc/articles/race_detector)
475 -- [staticcheck documentation](https://staticcheck.io/)
Makefile deleted
-43
@@ -1,43 +0,0 @@
1 -SHELL := /bin/sh
2 -
3 -.PHONY: server-up server-down server-build client-run chat-run build tidy clean
4 -
5 -# Docker Compose command (override with: make DC="docker-compose")
6 -DC ?= docker compose
7 -
8 -# --- Server (Docker) ---
9 -server-up:
10 - $(DC) up -d --build
11 -
12 -server-down:
13 - $(DC) down
14 -
15 -server-build:
16 - $(DC) build
17 -
18 -# --- Go SDK examples ---
19 -client-run:
20 - go run ./sdk/go/examples/http-client
21 -
22 -chat-run:
23 - go run ./sdk/go/examples/chat
24 -
25 -# --- Build binaries ---
26 -build:
27 - @echo "Building binaries..."
28 - @mkdir bin
29 - go build -trimpath -o bin/relaydns-server ./cmd/server
30 - go build -trimpath -o bin/relaydns-client ./sdk/go/examples/http-client
31 - go build -trimpath -o bin/relaydns-chat ./sdk/go/examples/chat
32 - @echo "Done: ./bin"
33 -
34 -# --- Module maintenance ---
35 -tidy:
36 - @echo "Syncing workspace and tidying modules..."
37 - @{ test -f go.work && go work sync || true; }
38 - go mod tidy
39 - (cd sdk/go && go mod tidy)
40 -
41 -clean:
42 - rm -rf bin coverage.out coverage.html
43 -
README.md deleted
-106
@@ -1,106 +0,0 @@
1 -# RelayDNS
2 -
3 -> A lightweight, DNS-driven peer-to-peer proxy layer built on libp2p.
4 -
5 -`relaydns` provides a minimal DNS-entry proxy that routes traffic between arbitrary nodes over **libp2p**.
6 -It lets you expose and discover TCP services (like SSH, API endpoints, etc.) even behind NAT,
7 -without depending on centralized reverse-proxy services.
8 -
9 -## Why RelayDNS?
10 -
11 -Traditional DNS and hosting rely on centralized servers and public IPs. DNSPortal closes that gap — serving as a lightweight bridge for peer discovery and connection.
12 -
13 -Think of it as the DNS layer for the peer-to-peer world:
14 -- It keeps discovery simple and human-readable (via DNS entries).
15 -- It connects peers that can’t directly see each other, acting as a neutral relay.
16 -- It gradually fades out once peers establish direct connectivity.
17 -
18 -It provides a clear, DNS-driven entrypoint to your peer network — letting decentralized services stay reachable without depending on fixed infrastructure or centralized gateways.
19 -
20 -## Features
21 -
22 -- **Peer-to-peer routing** over libp2p (supports hole punching, relay, pubsub)
23 -- **DNS-driven entrypoint** (server acts as a lightweight coordinator)
24 -- **Automatic peer advertisement** via GossipSub
25 -- **Pluggable client SDK** — embed the relaydns client directly into your Go applications
26 -
27 -## Architecture Overview
28 -
29 -```
30 -┌────────────┐ pubsub (GossipSub) ┌─────────────┐
31 -│ relay dns │ <---------------------> │ client(s) │
32 -│ server │ │(in your app)│
33 -└────────────┘ └─────────────┘
34 - │ │
35 - │ TCP stream (e.g. SSH, HTTP, custom) │
36 - ▼ ▼
37 - Your users Your local service
38 -```
39 -
40 -## Getting Started
41 -
42 -### 1. Run the Server (Docker Compose)
43 -
44 -```bash
45 -docker compose up --build -d
46 -```
47 -
48 -Published ports:
49 -- Admin/UI + HTTP proxy: `8080`
50 -- libp2p TCP/QUIC: `4001/tcp`, `4001/udp`
51 -
52 -### 2. (Optional) Run Example Clients
53 -
54 -Clients are NOT required to run the server. They are provided for testing/demo.
55 -
56 -- HTTP client (optional): exposes a tiny local HTTP backend and advertises it.
57 - ```bash
58 - make client-run
59 - # Optional overrides:
60 - # make client-run BACKEND_PORT=8081 SERVER_URL=http://localhost:8080
61 - ```
62 -
63 -- Chat client (optional): WebSocket chat UI (local) + advertiser (libp2p).
64 - ```bash
65 - make chat-run
66 - # Optional overrides:
67 - # make chat-run CHAT_PORT=8091 CHAT_NAME=demo-chat SERVER_URL=http://localhost:8080
68 - ```
69 -
70 -If you run the chat client:
71 -- Open locally: `http://localhost:8091`
72 -- Open via server proxy: Admin → your peer → Open (routes to `/peer/<peerID>/` then `/peer/<peerID>/ws`).
73 -
74 -### 3. Embed the Client SDK in Your App
75 -
76 -See SDK quickstarts and the protocol spec:
77 -- [Specification](./sdk/spec.md)
78 -- [Go](./sdk/go/README.md)
79 -- [TypeScript](./sdk/typescript/README.md)
80 -- [Python](./sdk/python/README.md)
81 -- [Rust](./sdk/rust/README.md)
82 -
83 -## Configuration Reference
84 -
85 -Server flags (see `docker-compose.yml`):
86 -- `--http` Unified admin UI + HTTP proxy listen address (default `:8080`)
87 -- `--bootstrap` Repeatable multiaddr with `/p2p/`
88 -
89 -HTTP client flags (see `make client-run`):
90 -- `--server-url` Admin base URL to fetch `/health` (default `http://localhost:8080`)
91 -- `--port` Local backend HTTP port (default `8081`)
92 -
93 -Chat client flags (see `make chat-run`):
94 -- `--server-url` Admin base URL to fetch `/health` (default `http://localhost:8080`)
95 -- `--port` Local chat HTTP port (default `8091`)
96 -- `--name` Display name (shown on server UI)
97 -
98 -## Deploying the Server (public)
99 -
100 -- Expose ports:
101 - - `8080/tcp` Admin UI + HTTP/WS proxy (`/peer/<peerID>/`) — flag: `--http-port`
102 - - `4001/tcp` and `4001/udp` libp2p (GossipSub/streams) — flag: `--p2p-port`
103 -- Cloudflare DNS:
104 - - Web UI/proxy (8080): can be proxied (orange cloud) if using HTTP/HTTPS
105 - - libp2p (4001 tcp/udp): must be DNS only (gray cloud). Cloudflare proxy doesn’t support arbitrary TCP/UDP ports.
106 -- WebSocket: server proxies 101 and tunnels bytes; the chat backend allows any HTTP(S) Origin for demo. Restrict in production.
buf.gen.yaml new
+12
@@ -0,0 +1,12 @@
1 +version: v2
2 +managed:
3 + enabled: true
4 +plugins:
5 + - local: protoc-gen-go
6 + out: .
7 + opt: paths=source_relative
8 + - local: protoc-gen-go-vtproto
9 + out: .
10 + opt: paths=source_relative
11 +inputs:
12 + - directory: proto
\ No newline at end of file
buf.yaml new
+8
@@ -0,0 +1,8 @@
1 +# For details on buf.yaml configuration, visit https://buf.build/docs/configuration/v2/buf-yaml
2 +version: v2
3 +lint:
4 + use:
5 + - STANDARD
6 +breaking:
7 + use:
8 + - FILE
docker-compose.yml
+2 -6
@@ -1,15 +1,11 @@
1 -version: "3.9"
2 -
1 services:
2 relayserver:
3 build:
4 context: .
5 dockerfile: Dockerfile
8 - image: dreamcacao/relaydns:latest
6 command:
7 - "--http-port"
8 - "19080"
12 - - "--p2p-port"
13 - - "4001"
14 - network_mode: "host"
9 + ports:
10 + - "19080:19080"
11 restart: unless-stopped
go.mod
+8 -58
@@ -3,21 +3,21 @@ module github.com/gosuda/relaydns
3 go 1.25.3
4
5 require (
6 - github.com/cockroachdb/crlib v0.0.0-20251001180057-2a49e1873587
6 github.com/cockroachdb/pebble v1.1.5
7 github.com/go-chi/chi/v5 v5.2.3
8 github.com/gorilla/websocket v1.5.3
9 + github.com/gosuda/relaydns/sdk/go v0.0.0-20251022064639-15f1536463b4
10 + github.com/hashicorp/yamux v0.1.2
11 github.com/libp2p/go-libp2p v0.44.0
11 - github.com/libp2p/go-libp2p-pubsub v0.15.0
12 - github.com/multiformats/go-multiaddr v0.16.0
12 + github.com/planetscale/vtprotobuf v0.6.0
13 github.com/rs/zerolog v1.34.0
14 github.com/spf13/cobra v1.10.1
15 - golang.org/x/crypto v0.41.0
15 + github.com/valyala/bytebufferpool v1.0.0
16 + google.golang.org/protobuf v1.36.6
17 )
18
19 require (
20 github.com/DataDog/zstd v1.4.5 // indirect
20 - github.com/benbjohnson/clock v1.3.5 // indirect
21 github.com/beorn7/perks v1.0.1 // indirect
22 github.com/cespare/xxhash/v2 v2.3.0 // indirect
23 github.com/cockroachdb/errors v1.11.3 // indirect
@@ -25,43 +25,27 @@ require (
25 github.com/cockroachdb/logtags v0.0.0-20230118201751-21c54148d20b // indirect
26 github.com/cockroachdb/redact v1.1.5 // indirect
27 github.com/cockroachdb/tokenbucket v0.0.0-20230807174530-cc333fc44b06 // indirect
28 - github.com/davidlazar/go-crypto v0.0.0-20200604182044-b73af7476f6c // indirect
28 github.com/decred/dcrd/dcrec/secp256k1/v4 v4.4.0 // indirect
30 - github.com/flynn/noise v1.1.0 // indirect
31 - github.com/francoispqt/gojay v1.2.13 // indirect
29 github.com/getsentry/sentry-go v0.27.0 // indirect
30 github.com/gogo/protobuf v1.3.2 // indirect
31 github.com/golang/snappy v0.0.4 // indirect
35 - github.com/google/uuid v1.6.0 // indirect
32 github.com/hashicorp/golang-lru/v2 v2.0.7 // indirect
37 - github.com/huin/goupnp v1.3.0 // indirect
33 github.com/inconshreveable/mousetrap v1.1.0 // indirect
34 github.com/ipfs/go-cid v0.5.0 // indirect
40 - github.com/jackpal/go-nat-pmp v1.0.2 // indirect
41 - github.com/jbenet/go-temp-err-catcher v0.1.0 // indirect
35 github.com/klauspost/compress v1.18.0 // indirect
36 github.com/klauspost/cpuid/v2 v2.2.10 // indirect
44 - github.com/koron/go-ssdp v0.0.6 // indirect
37 github.com/kr/pretty v0.3.1 // indirect
38 github.com/kr/text v0.2.0 // indirect
39 github.com/libp2p/go-buffer-pool v0.1.0 // indirect
48 - github.com/libp2p/go-flow-metrics v0.2.0 // indirect
49 - github.com/libp2p/go-libp2p-asn-util v0.4.1 // indirect
40 + github.com/libp2p/go-libp2p-pubsub v0.15.0 // indirect
41 github.com/libp2p/go-msgio v0.3.0 // indirect
51 - github.com/libp2p/go-netroute v0.3.0 // indirect
52 - github.com/libp2p/go-reuseport v0.4.0 // indirect
53 - github.com/libp2p/go-yamux/v5 v5.0.1 // indirect
54 - github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd // indirect
42 github.com/mattn/go-colorable v0.1.13 // indirect
43 github.com/mattn/go-isatty v0.0.20 // indirect
57 - github.com/miekg/dns v1.1.66 // indirect
58 - github.com/mikioh/tcpinfo v0.0.0-20190314235526-30a79bb1804b // indirect
59 - github.com/mikioh/tcpopt v0.0.0-20190314235656-172688c1accc // indirect
44 github.com/minio/sha256-simd v1.0.1 // indirect
45 github.com/mr-tron/base58 v1.2.0 // indirect
46 github.com/multiformats/go-base32 v0.1.0 // indirect
47 github.com/multiformats/go-base36 v0.2.0 // indirect
64 - github.com/multiformats/go-multiaddr-dns v0.4.1 // indirect
48 + github.com/multiformats/go-multiaddr v0.16.0 // indirect
49 github.com/multiformats/go-multiaddr-fmt v0.1.0 // indirect
50 github.com/multiformats/go-multibase v0.2.0 // indirect
51 github.com/multiformats/go-multicodec v0.9.1 // indirect
@@ -69,51 +53,17 @@ require (
53 github.com/multiformats/go-multistream v0.6.1 // indirect
54 github.com/multiformats/go-varint v0.0.7 // indirect
55 github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect
72 - github.com/pbnjay/memory v0.0.0-20210728143218-7b4eea64cf58 // indirect
73 - github.com/pion/datachannel v1.5.10 // indirect
74 - github.com/pion/dtls/v2 v2.2.12 // indirect
75 - github.com/pion/dtls/v3 v3.0.6 // indirect
76 - github.com/pion/ice/v4 v4.0.10 // indirect
77 - github.com/pion/interceptor v0.1.40 // indirect
78 - github.com/pion/logging v0.2.3 // indirect
79 - github.com/pion/mdns/v2 v2.0.7 // indirect
80 - github.com/pion/randutil v0.1.0 // indirect
81 - github.com/pion/rtcp v1.2.15 // indirect
82 - github.com/pion/rtp v1.8.19 // indirect
83 - github.com/pion/sctp v1.8.39 // indirect
84 - github.com/pion/sdp/v3 v3.0.13 // indirect
85 - github.com/pion/srtp/v3 v3.0.6 // indirect
86 - github.com/pion/stun v0.6.1 // indirect
87 - github.com/pion/stun/v3 v3.0.0 // indirect
88 - github.com/pion/transport/v2 v2.2.10 // indirect
89 - github.com/pion/transport/v3 v3.0.7 // indirect
90 - github.com/pion/turn/v4 v4.0.2 // indirect
91 - github.com/pion/webrtc/v4 v4.1.2 // indirect
56 github.com/pkg/errors v0.9.1 // indirect
57 github.com/prometheus/client_golang v1.22.0 // indirect
58 github.com/prometheus/client_model v0.6.2 // indirect
59 github.com/prometheus/common v0.64.0 // indirect
60 github.com/prometheus/procfs v0.16.1 // indirect
97 - github.com/quic-go/qpack v0.5.1 // indirect
98 - github.com/quic-go/quic-go v0.55.0 // indirect
99 - github.com/quic-go/webtransport-go v0.9.0 // indirect
61 github.com/rogpeppe/go-internal v1.10.0 // indirect
62 github.com/spaolacci/murmur3 v1.1.0 // indirect
63 github.com/spf13/pflag v1.0.9 // indirect
103 - github.com/wlynxg/anet v0.0.5 // indirect
104 - go.uber.org/dig v1.19.0 // indirect
105 - go.uber.org/fx v1.24.0 // indirect
106 - go.uber.org/mock v0.5.2 // indirect
107 - go.uber.org/multierr v1.11.0 // indirect
108 - go.uber.org/zap v1.27.0 // indirect
64 + golang.org/x/crypto v0.41.0 // indirect
65 golang.org/x/exp v0.0.0-20250606033433-dcc06ee1d476 // indirect
110 - golang.org/x/mod v0.27.0 // indirect
111 - golang.org/x/net v0.43.0 // indirect
112 - golang.org/x/sync v0.16.0 // indirect
66 golang.org/x/sys v0.35.0 // indirect
67 golang.org/x/text v0.28.0 // indirect
115 - golang.org/x/time v0.12.0 // indirect
116 - golang.org/x/tools v0.36.0 // indirect
117 - google.golang.org/protobuf v1.36.6 // indirect
68 lukechampine.com/blake3 v1.4.1 // indirect
69 )
go.sum
+9 -220
@@ -1,28 +1,11 @@
1 -cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
2 -cloud.google.com/go v0.31.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
3 -cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
4 -cloud.google.com/go v0.37.0/go.mod h1:TS1dMSSfndXH133OKGwekG838Om/cQT0BUHV3HcBgoo=
5 -dmitri.shuralyov.com/app/changes v0.0.0-20180602232624-0a106ad413e3/go.mod h1:Yl+fi1br7+Rr3LqpNJf1/uxUdtRUV+Tnj0o93V2B9MU=
6 -dmitri.shuralyov.com/html/belt v0.0.0-20180602232347-f7d459c86be0/go.mod h1:JLBrvjyP0v+ecvNYvCpyZgu5/xkfAUhi6wJj28eUfSU=
7 -dmitri.shuralyov.com/service/change v0.0.0-20181023043359-a85b471d5412/go.mod h1:a1inKt/atXimZ4Mv927x+r7UpyzRUf4emIoiiSC2TN4=
8 -dmitri.shuralyov.com/state v0.0.0-20180228185332-28bcc343414c/go.mod h1:0PRwlb0D6DFvNNtx+9ybjezNCa8XF0xaYcETyp6rHWU=
9 -git.apache.org/thrift.git v0.0.0-20180902110319-2566ecd5d999/go.mod h1:fPE2ZNJGynbRyZ4dJvy6G277gSllfV2HJqblrnkyeyg=
10 -github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
1 github.com/DataDog/zstd v1.4.5 h1:EndNeuB0l9syBZhut0wns3gV1hL8zX8LIu6ZiVHWLIQ=
2 github.com/DataDog/zstd v1.4.5/go.mod h1:1jcaCB/ufaK+sKp1NBhlGmpz41jOoPQ35bpF36t7BBo=
13 -github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c=
3 github.com/benbjohnson/clock v1.3.5 h1:VvXlSJBzZpA/zum6Sj74hxwYI2DIxRWuNIoXAzHZz5o=
4 github.com/benbjohnson/clock v1.3.5/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
16 -github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q=
5 github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM=
6 github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw=
19 -github.com/bradfitz/go-smtpd v0.0.0-20170404230938-deb6d6237625/go.mod h1:HYsPBTaaSFSlLx/70C2HPIMNZpVV8+vt/A+FMnYP11g=
20 -github.com/buger/jsonparser v0.0.0-20181115193947-bf1c66bbce23/go.mod h1:bbYlZJ7hK1yFx9hf58LP0zeX7UjIGs20ufpu3evjr+s=
7 github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs=
8 github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
23 -github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
24 -github.com/cockroachdb/crlib v0.0.0-20251001180057-2a49e1873587 h1:qjG2TrBrPbGRVYp5obcAi8OSsuFJ8s1AElDImHLV9tY=
25 -github.com/cockroachdb/crlib v0.0.0-20251001180057-2a49e1873587/go.mod h1:ae57yNis2F1FThSNdPdoXfiPOVi8G1TLreCBQYPOdqo=
9 github.com/cockroachdb/datadriven v1.0.3-0.20230413201302-be42291fc80f h1:otljaYPt5hWxV3MUfO5dFPFiOXg9CyG5/kCfayTqsJ4=
10 github.com/cockroachdb/datadriven v1.0.3-0.20230413201302-be42291fc80f/go.mod h1:a9RdTaap04u637JoCzcUoIcDmvwSUtcUFtT/C3kJlTU=
11 github.com/cockroachdb/errors v1.11.3 h1:5bA+k2Y6r+oz/6Z/RFlNeVCesGARKuC6YymtcDrbC/I=
@@ -37,11 +20,9 @@ github.com/cockroachdb/redact v1.1.5 h1:u1PMllDkdFfPWaNGMyLD1+so+aq3uUItthCFqzwP
20 github.com/cockroachdb/redact v1.1.5/go.mod h1:BVNblN9mBWFyMyqK1k3AAiSxhvhfK2oOZZ2lK+dpvRg=
21 github.com/cockroachdb/tokenbucket v0.0.0-20230807174530-cc333fc44b06 h1:zuQyyAKVxetITBuuhv3BI9cMrmStnpT18zmgmTxunpo=
22 github.com/cockroachdb/tokenbucket v0.0.0-20230807174530-cc333fc44b06/go.mod h1:7nc4anLGjupUW/PeY5qiNYsdNXj7zopG+eqsS7To5IQ=
40 -github.com/coreos/go-systemd v0.0.0-20181012123002-c6f51f82210d/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
23 github.com/coreos/go-systemd/v22 v22.5.0/go.mod h1:Y58oyj3AT4RCenI/lSvhwexgC+NSVTIJ3seZv2GcEnc=
24 github.com/cpuguy83/go-md2man/v2 v2.0.6/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g=
25 github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E=
44 -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
26 github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
27 github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
28 github.com/davidlazar/go-crypto v0.0.0-20200604182044-b73af7476f6c h1:pFUpOrbxDR6AkioZ1ySsx5yxlDQZ8stG2b88gTPxgJU=
@@ -50,53 +31,33 @@ github.com/decred/dcrd/crypto/blake256 v1.1.0 h1:zPMNGQCm0g4QTY27fOCorQW7EryeQ/U
31 github.com/decred/dcrd/crypto/blake256 v1.1.0/go.mod h1:2OfgNZ5wDpcsFmHmCK5gZTPcCXqlm2ArzUIkw9czNJo=
32 github.com/decred/dcrd/dcrec/secp256k1/v4 v4.4.0 h1:NMZiJj8QnKe1LgsbDayM4UoHwbvwDRwnI3hwNaAHRnc=
33 github.com/decred/dcrd/dcrec/secp256k1/v4 v4.4.0/go.mod h1:ZXNYxsqcloTdSy/rNShjYzMhyjf0LaoftYK0p+A3h40=
53 -github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
54 -github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc=
34 github.com/flynn/noise v1.1.0 h1:KjPQoQCEFdZDiP03phOvGi11+SVVhBG2wOWAorLsstg=
35 github.com/flynn/noise v1.1.0/go.mod h1:xbMo+0i6+IGbYdJhF31t2eR1BIU0CYc12+BNAKwUTag=
36 github.com/francoispqt/gojay v1.2.13 h1:d2m3sFjloqoIUQU3TsHBgj6qg/BVGlTBeHDUmyJnXKk=
37 github.com/francoispqt/gojay v1.2.13/go.mod h1:ehT5mTG4ua4581f1++1WLG0vPdaA9HaiDsoyrBGkyDY=
59 -github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
38 github.com/getsentry/sentry-go v0.27.0 h1:Pv98CIbtB3LkMWmXi4Joa5OOcwbmnX88sF5qbK3r3Ps=
39 github.com/getsentry/sentry-go v0.27.0/go.mod h1:lc76E2QywIyW8WuBnwl8Lc4bkmQH4+w1gwTf25trprY=
62 -github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
63 -github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0=
40 github.com/go-chi/chi/v5 v5.2.3 h1:WQIt9uxdsAbgIYgid+BpYc+liqQZGMHRaUwp0JUcvdE=
41 github.com/go-chi/chi/v5 v5.2.3/go.mod h1:L2yAIGWB3H+phAw1NxKwWM+7eUH/lU8pOMm5hHcoops=
66 -github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q=
42 github.com/go-errors/errors v1.4.2 h1:J6MZopCL4uSllY1OfXM374weqZFFItUbrImctkmUxIA=
43 github.com/go-errors/errors v1.4.2/go.mod h1:sIVyrIiJhuEF+Pj9Ebtd6P/rEYROXFi3BopGUQ5a5Og=
44 github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA=
70 -github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
45 github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q=
46 github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q=
73 -github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
74 -github.com/golang/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:tluoj9z5200jBnyusfRPU2LqT6J+DAorxEvtC7LHB+E=
75 -github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
76 -github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
77 -github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
78 -github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
47 github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM=
48 github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
81 -github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
82 -github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
49 github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8=
50 github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU=
85 -github.com/google/go-github v17.0.0+incompatible/go.mod h1:zLgOLi98H3fifZn+44m+umXrS52loVEgC2AApnigrVQ=
86 -github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck=
87 -github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs=
88 -github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc=
51 github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
52 github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
91 -github.com/googleapis/gax-go v2.0.0+incompatible/go.mod h1:SFVmujtThgffbyetf+mdk2eWhX2bMyUtNHzFKcPA9HY=
92 -github.com/googleapis/gax-go/v2 v2.0.3/go.mod h1:LLvjysVCY1JZeum8Z6l8qUty8fiNwE08qbEPm1M08qg=
93 -github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY=
53 github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg=
54 github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE=
96 -github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA=
97 -github.com/grpc-ecosystem/grpc-gateway v1.5.0/go.mod h1:RSKVYQBd5MCa4OVpNdGskqpgL2+G+NZTnrVHpWWfpdw=
55 +github.com/gosuda/relaydns/sdk/go v0.0.0-20251022064639-15f1536463b4 h1:6Gmf+J6VuKE9DObZnviKL3AldnZROMecDpq/8g9kDTM=
56 +github.com/gosuda/relaydns/sdk/go v0.0.0-20251022064639-15f1536463b4/go.mod h1:NSKO/60gyDV/dOQlPNCB1fZbTehHVu2YcnUfWKSELpk=
57 github.com/hashicorp/golang-lru/v2 v2.0.7 h1:a+bsQ5rvGLjzHuww6tVxozPZFVghXaHOwFs4luLUK2k=
58 github.com/hashicorp/golang-lru/v2 v2.0.7/go.mod h1:QeFd9opnmA6QUJc5vARoKUSoFhyfM2/ZepoAG6RGpeM=
59 +github.com/hashicorp/yamux v0.1.2 h1:XtB8kyFOyHXYVFnwT5C3+Bdo8gArse7j2AQ0DA0Uey8=
60 +github.com/hashicorp/yamux v0.1.2/go.mod h1:C+zze2n6e/7wshOZep2A70/aQU6QBRWJO/G6FT1wIns=
61 github.com/huin/goupnp v1.3.0 h1:UvLUlWDNpoUdYzb2TCn+MuTWtcjXKSza2n6CBdQ0xXc=
62 github.com/huin/goupnp v1.3.0/go.mod h1:gnGPsThkYa7bFi/KWmEysQRf48l2dvR5bxr2OFckNX8=
63 github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8=
@@ -107,9 +68,6 @@ github.com/jackpal/go-nat-pmp v1.0.2 h1:KzKSgb7qkJvOUTqYl9/Hg/me3pWgBmERKrTGD7Bd
68 github.com/jackpal/go-nat-pmp v1.0.2/go.mod h1:QPH045xvCAeXUZOxsnwmrtiCoxIr9eob+4orBN1SBKc=
69 github.com/jbenet/go-temp-err-catcher v0.1.0 h1:zpb3ZH6wIE8Shj2sKS+khgRvf7T7RABoLk/+KKHggpk=
70 github.com/jbenet/go-temp-err-catcher v0.1.0/go.mod h1:0kJRvmDZXNMIiJirNPEYfhpPwbGVtZVWC34vc5WLsDk=
110 -github.com/jellevandenhooff/dkim v0.0.0-20150330215556-f50fe3d243e1/go.mod h1:E0B/fFc00Y+Rasa88328GlI/XbtyysCtTHZS8h7IrBU=
111 -github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU=
112 -github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU=
71 github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8=
72 github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
73 github.com/klauspost/compress v1.18.0 h1:c/Cqfb0r+Yi+JtIEq73FWXVkRonBlf0CRNYc8Zttxdo=
@@ -118,13 +76,8 @@ github.com/klauspost/cpuid/v2 v2.2.10 h1:tBs3QSyvjDyFTq3uoc/9xFpCuOsJQFNPiAhYdw2
76 github.com/klauspost/cpuid/v2 v2.2.10/go.mod h1:hqwkgyIinND0mEev00jJYCxPNVRVXFQeu1XKlok6oO0=
77 github.com/koron/go-ssdp v0.0.6 h1:Jb0h04599eq/CY7rB5YEqPS83HmRfHP2azkxMN2rFtU=
78 github.com/koron/go-ssdp v0.0.6/go.mod h1:0R9LfRJGek1zWTjN3JUNlm5INCDYGpRDfAptnct63fI=
121 -github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
122 -github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
79 github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
80 github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk=
125 -github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
126 -github.com/kr/pty v1.1.3/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
127 -github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
81 github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
82 github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
83 github.com/libp2p/go-buffer-pool v0.1.0 h1:oK4mSFcQz7cTQIfqbe4MIj9gLW+mnanjyFtc6cdF0Y8=
@@ -147,10 +100,6 @@ github.com/libp2p/go-reuseport v0.4.0 h1:nR5KU7hD0WxXCJbmw7r2rhRYruNRl2koHw8fQsc
100 github.com/libp2p/go-reuseport v0.4.0/go.mod h1:ZtI03j/wO5hZVDFo2jKywN6bYKWLOy8Se6DrI2E1cLU=
101 github.com/libp2p/go-yamux/v5 v5.0.1 h1:f0WoX/bEF2E8SbE4c/k1Mo+/9z0O4oC/hWEA+nfYRSg=
102 github.com/libp2p/go-yamux/v5 v5.0.1/go.mod h1:en+3cdX51U0ZslwRdRLrvQsdayFt3TSUKvBGErzpWbU=
150 -github.com/lunixbochs/vtclean v1.0.0/go.mod h1:pHhQNgMf3btfWnGBVipUOjRYhoOsdGqdm/+2c2E2WMI=
151 -github.com/mailru/easyjson v0.0.0-20190312143242-1de009706dbe/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
152 -github.com/marcopolo/simnet v0.0.1 h1:rSMslhPz6q9IvJeFWDoMGxMIrlsbXau3NkuIXHGJxfg=
153 -github.com/marcopolo/simnet v0.0.1/go.mod h1:WDaQkgLAjqDUEBAOXz22+1j6wXKfGlC5sD5XWt3ddOs=
103 github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd h1:br0buuQ854V8u83wA0rVZ8ttrq5CpaPZdvrK0LP2lOk=
104 github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd/go.mod h1:QuCEs1Nt24+FYQEqAAncTDPJIuGs+LxK1MCiFL25pMU=
105 github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA=
@@ -159,12 +108,8 @@ github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/
108 github.com/mattn/go-isatty v0.0.19/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
109 github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
110 github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
162 -github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0=
163 -github.com/microcosm-cc/bluemonday v1.0.1/go.mod h1:hsXNsILzKxV+sX77C5b8FSuKF00vh2OMYv+xgHpAMF4=
111 github.com/miekg/dns v1.1.66 h1:FeZXOS3VCVsKnEAd+wBkjMC3D2K+ww66Cq3VnCINuJE=
112 github.com/miekg/dns v1.1.66/go.mod h1:jGFzBsSNbJw6z1HYut1RKBKHA9PBdxeHrZG8J+gC2WE=
166 -github.com/mikioh/tcp v0.0.0-20190314235350-803a9b46060c h1:bzE/A84HN25pxAuk9Eej1Kz9OUelF97nAc82bDquQI8=
167 -github.com/mikioh/tcp v0.0.0-20190314235350-803a9b46060c/go.mod h1:0SQS9kMwD2VsyFEB++InYyBJroV/FRmBgcydeSUcJms=
113 github.com/mikioh/tcpinfo v0.0.0-20190314235526-30a79bb1804b h1:z78hV3sbSMAUoyUMM0I83AUIT6Hu17AWfgjzIbtrYFc=
114 github.com/mikioh/tcpinfo v0.0.0-20190314235526-30a79bb1804b/go.mod h1:lxPUiZwKoFL8DUUmalo2yJJUCxbPKtm8OKfqr2/FTNU=
115 github.com/mikioh/tcpopt v0.0.0-20190314235656-172688c1accc h1:PTfri+PuQmWDqERdnNMiD9ZejrlswWrCpBEZgWOiTrc=
@@ -173,8 +118,6 @@ github.com/minio/blake2b-simd v0.0.0-20160723061019-3f5f724cb5b1/go.mod h1:pD8Rv
118 github.com/minio/sha256-simd v0.1.1-0.20190913151208-6de447530771/go.mod h1:B5e1o+1/KgNmWrSQK08Y6Z1Vb5pwIktudl0J58iy0KM=
119 github.com/minio/sha256-simd v1.0.1 h1:6kaan5IFmwTNynnKKpDHe6FWHohJOHhCPchzK49dzMM=
120 github.com/minio/sha256-simd v1.0.1/go.mod h1:Pz6AKMiUdngCLpeTL/RJY1M9rUuPMYujV5xJjtbRSN8=
176 -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
177 -github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0=
121 github.com/mr-tron/base58 v1.1.2/go.mod h1:BinMc/sQntlIE1frQmRFPUoPA1Zkr8VRgBdjWI2mNwc=
122 github.com/mr-tron/base58 v1.2.0 h1:T/HDJBh4ZCPbU39/+c3rRvE0uKBQlU27+QI8LJ4t64o=
123 github.com/mr-tron/base58 v1.2.0/go.mod h1:BinMc/sQntlIE1frQmRFPUoPA1Zkr8VRgBdjWI2mNwc=
@@ -202,16 +145,12 @@ github.com/multiformats/go-varint v0.0.7 h1:sWSGR+f/eu5ABZA2ZpYKBILXTTs9JWpdEM/n
145 github.com/multiformats/go-varint v0.0.7/go.mod h1:r8PUYw/fD/SjBCiKOoDlGF6QawOELpZAu9eioSos/OU=
146 github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 h1:C3w9PqII01/Oq1c1nUAm88MOHcQC9l5mIlSMApZMrHA=
147 github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ=
205 -github.com/neelance/astrewrite v0.0.0-20160511093645-99348263ae86/go.mod h1:kHJEU3ofeGjhHklVoIGuVj85JJwZ6kWPaJwCIxgnFmo=
206 -github.com/neelance/sourcemap v0.0.0-20151028013722-8c68805598ab/go.mod h1:Qr6/a/Q4r9LP1IltGz7tA7iOK1WonHEYhu1HRBA7ZiM=
207 -github.com/openzipkin/zipkin-go v0.1.1/go.mod h1:NtoC/o8u3JlF1lSlyPNswIbeQH9bJTmOf0Erfk+hxe8=
148 github.com/pbnjay/memory v0.0.0-20210728143218-7b4eea64cf58 h1:onHthvaw9LFnH4t2DcNVpwGmV9E1BkGknEliJkfwQj0=
149 github.com/pbnjay/memory v0.0.0-20210728143218-7b4eea64cf58/go.mod h1:DXv8WO4yhMYhSNPKjeNKa5WY9YCIEBRbNzFFPJbWO6Y=
150 github.com/pingcap/errors v0.11.4 h1:lFuQV/oaUMGcD2tqt+01ROSmJs75VG1ToEOkZIZ4nE4=
151 github.com/pingcap/errors v0.11.4/go.mod h1:Oi8TUi2kEtXXLMJk9l1cGmz20kV3TaQ0usTwv5KuLY8=
152 github.com/pion/datachannel v1.5.10 h1:ly0Q26K1i6ZkGf42W7D4hQYR90pZwzFOjTq5AuCKk4o=
153 github.com/pion/datachannel v1.5.10/go.mod h1:p/jJfC9arb29W7WrxyKbepTU20CFgyx5oLo8Rs4Py/M=
214 -github.com/pion/dtls/v2 v2.2.7/go.mod h1:8WiMkebSHFD0T+dIU+UeBaoV7kDhOW5oDCzZ7WZ/F9s=
154 github.com/pion/dtls/v2 v2.2.12 h1:KP7H5/c1EiVAAKUmXyCzPiQe5+bCJrpOeKg/L05dunk=
155 github.com/pion/dtls/v2 v2.2.12/go.mod h1:d9SYc9fch0CqK90mRk1dC7AkzzpwJj6u2GU3u+9pqFE=
156 github.com/pion/dtls/v3 v3.0.6 h1:7Hkd8WhAJNbRgq9RgdNh1aaWlZlGpYTzdqjy9x9sK2E=
@@ -220,9 +159,9 @@ github.com/pion/ice/v4 v4.0.10 h1:P59w1iauC/wPk9PdY8Vjl4fOFL5B+USq1+xbDcN6gT4=
159 github.com/pion/ice/v4 v4.0.10/go.mod h1:y3M18aPhIxLlcO/4dn9X8LzLLSma84cx6emMSu14FGw=
160 github.com/pion/interceptor v0.1.40 h1:e0BjnPcGpr2CFQgKhrQisBU7V3GXK6wrfYrGYaU6Jq4=
161 github.com/pion/interceptor v0.1.40/go.mod h1:Z6kqH7M/FYirg3frjGJ21VLSRJGBXB/KqaTIrdqnOic=
223 -github.com/pion/logging v0.2.2/go.mod h1:k0/tDVsRCX2Mb2ZEmTqNa7CWsQPc+YYCB7Q+5pahoms=
162 github.com/pion/logging v0.2.3 h1:gHuf0zpoh1GW67Nr6Gj4cv5Z9ZscU7g/EaoC/Ke/igI=
163 github.com/pion/logging v0.2.3/go.mod h1:z8YfknkquMe1csOrxK5kc+5/ZPAzMxbKLX5aXpbpC90=
164 +github.com/pion/mdns v0.0.12 h1:CiMYlY+O0azojWDmxdNr7ADGrnZ+V6Ilfner+6mSVK8=
165 github.com/pion/mdns/v2 v2.0.7 h1:c9kM8ewCgjslaAmicYMFQIde2H9/lrZpjBkN8VwoVtM=
166 github.com/pion/mdns/v2 v2.0.7/go.mod h1:vAdSYNAT0Jy3Ru0zl2YiW3Rm/fJCwIeM0nToenfOJKA=
167 github.com/pion/randutil v0.1.0 h1:CFG1UdESneORglEsnimhUjf33Rwjubwj6xfiOXBa3mA=
@@ -241,8 +180,6 @@ github.com/pion/stun v0.6.1 h1:8lp6YejULeHBF8NmV8e2787BogQhduZugh5PdhDyyN4=
180 github.com/pion/stun v0.6.1/go.mod h1:/hO7APkX4hZKu/D0f2lHzNyvdkTGtIy3NDmLR7kSz/8=
181 github.com/pion/stun/v3 v3.0.0 h1:4h1gwhWLWuZWOJIJR9s2ferRO+W3zA/b6ijOI6mKzUw=
182 github.com/pion/stun/v3 v3.0.0/go.mod h1:HvCN8txt8mwi4FBvS3EmDghW6aQJ24T+y+1TKjB5jyU=
244 -github.com/pion/transport/v2 v2.2.1/go.mod h1:cXXWavvCnFF6McHTft3DWS9iic2Mftcz1Aq29pGcU5g=
245 -github.com/pion/transport/v2 v2.2.4/go.mod h1:q2U/tf9FEfnSBGSW6w5Qp5PFWRLRj3NjLhCCgpRK4p0=
183 github.com/pion/transport/v2 v2.2.10 h1:ucLBLE8nuxiHfvkFKnkDQRYWYfp8ejf4YBOPfaQpw6Q=
184 github.com/pion/transport/v2 v2.2.10/go.mod h1:sq1kSLWs+cHW9E+2fJP95QudkzbK7wscs8yYgQToO5E=
185 github.com/pion/transport/v3 v3.0.7 h1:iRbMH05BzSNwhILHoBoAPxoB9xQgOaJk+591KC9P1o0=
@@ -252,21 +189,18 @@ github.com/pion/turn/v4 v4.0.2/go.mod h1:pMMKP/ieNAG/fN5cZiN4SDuyKsXtNTr0ccN7ITo
189 github.com/pion/webrtc/v4 v4.1.2 h1:mpuUo/EJ1zMNKGE79fAdYNFZBX790KE7kQQpLMjjR54=
190 github.com/pion/webrtc/v4 v4.1.2/go.mod h1:xsCXiNAmMEjIdFxAYU0MbB3RwRieJsegSB2JZsGN+8U=
191 github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA=
255 -github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
192 github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
193 github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
194 +github.com/planetscale/vtprotobuf v0.6.0 h1:nBeETjudeJ5ZgBHUz1fVHvbqUKnYOXNhsIEabROxmNA=
195 +github.com/planetscale/vtprotobuf v0.6.0/go.mod h1:t/avpk3KcrXxUnYOhZhMXJlSEyie6gQbtLq5NM3loB8=
196 github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
197 github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
260 -github.com/prometheus/client_golang v0.8.0/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw=
198 github.com/prometheus/client_golang v1.22.0 h1:rb93p9lokFEsctTys46VnV1kLCDpVZ0a/Y92Vm0Zc6Q=
199 github.com/prometheus/client_golang v1.22.0/go.mod h1:R7ljNsLXhuQXYZYtw6GAE9AZg8Y7vEW5scdCXrWRXC0=
263 -github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
200 github.com/prometheus/client_model v0.6.2 h1:oBsgwpGs7iVziMvrGhE53c/GrLUsZdHnqNwqPLxwZyk=
201 github.com/prometheus/client_model v0.6.2/go.mod h1:y3m2F6Gdpfy6Ut/GBsUqTWZqCUvMVzSfMLjcu6wAwpE=
266 -github.com/prometheus/common v0.0.0-20180801064454-c7de2306084e/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro=
202 github.com/prometheus/common v0.64.0 h1:pdZeA+g617P7oGv1CzdTzyeShxAGrTBsolKNOLQPGO4=
203 github.com/prometheus/common v0.64.0/go.mod h1:0gZns+BLRQ3V6NdaerOhMbwwRbNh9hkGINtQAsP5GS8=
269 -github.com/prometheus/procfs v0.0.0-20180725123919-05ee40e3a273/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk=
204 github.com/prometheus/procfs v0.16.1 h1:hZ15bTNuirocR6u0JZ6BAHHmwS1p8B4P6MRqxtzMyRg=
205 github.com/prometheus/procfs v0.16.1/go.mod h1:teAbpZRB1iIAJYREa1LsoWUXykVXA1KlTmWl8x/U+Is=
206 github.com/quic-go/qpack v0.5.1 h1:giqksBPnT/HDtZ6VhtFKgoLOWmlyo9Ei6u9PqzIMbhI=
@@ -281,59 +215,21 @@ github.com/rogpeppe/go-internal v1.10.0/go.mod h1:UQnix2H7Ngw/k4C5ijL5+65zddjncj
215 github.com/rs/xid v1.6.0/go.mod h1:7XoLgs4eV+QndskICGsho+ADou8ySMSjJKDIan90Nz0=
216 github.com/rs/zerolog v1.34.0 h1:k43nTLIwcTVQAncfCw4KZ2VY6ukYoZaBPNOE8txlOeY=
217 github.com/rs/zerolog v1.34.0/go.mod h1:bJsvje4Z08ROH4Nhs5iH600c3IkWhwp44iRc54W6wYQ=
284 -github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g=
218 github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
286 -github.com/sergi/go-diff v1.0.0/go.mod h1:0CfEIISq7TuYL3j771MWULgwwjU+GofnZX9QAmXWZgo=
287 -github.com/shurcooL/component v0.0.0-20170202220835-f88ec8f54cc4/go.mod h1:XhFIlyj5a1fBNx5aJTbKoIq0mNaPvOagO+HjB3EtxrY=
288 -github.com/shurcooL/events v0.0.0-20181021180414-410e4ca65f48/go.mod h1:5u70Mqkb5O5cxEA8nxTsgrgLehJeAw6Oc4Ab1c/P1HM=
289 -github.com/shurcooL/github_flavored_markdown v0.0.0-20181002035957-2122de532470/go.mod h1:2dOwnU2uBioM+SGy2aZoq1f/Sd1l9OkAeAUvjSyvgU0=
290 -github.com/shurcooL/go v0.0.0-20180423040247-9e1955d9fb6e/go.mod h1:TDJrrUr11Vxrven61rcy3hJMUqaf/CLWYhHNPmT14Lk=
291 -github.com/shurcooL/go-goon v0.0.0-20170922171312-37c2f522c041/go.mod h1:N5mDOmsrJOB+vfqUK+7DmDyjhSLIIBnXo9lvZJj3MWQ=
292 -github.com/shurcooL/gofontwoff v0.0.0-20180329035133-29b52fc0a18d/go.mod h1:05UtEgK5zq39gLST6uB0cf3NEHjETfB4Fgr3Gx5R9Vw=
293 -github.com/shurcooL/gopherjslib v0.0.0-20160914041154-feb6d3990c2c/go.mod h1:8d3azKNyqcHP1GaQE/c6dDgjkgSx2BZ4IoEi4F1reUI=
294 -github.com/shurcooL/highlight_diff v0.0.0-20170515013008-09bb4053de1b/go.mod h1:ZpfEhSmds4ytuByIcDnOLkTHGUI6KNqRNPDLHDk+mUU=
295 -github.com/shurcooL/highlight_go v0.0.0-20181028180052-98c3abbbae20/go.mod h1:UDKB5a1T23gOMUJrI+uSuH0VRDStOiUVSjBTRDVBVag=
296 -github.com/shurcooL/home v0.0.0-20181020052607-80b7ffcb30f9/go.mod h1:+rgNQw2P9ARFAs37qieuu7ohDNQ3gds9msbT2yn85sg=
297 -github.com/shurcooL/htmlg v0.0.0-20170918183704-d01228ac9e50/go.mod h1:zPn1wHpTIePGnXSHpsVPWEktKXHr6+SS6x/IKRb7cpw=
298 -github.com/shurcooL/httperror v0.0.0-20170206035902-86b7830d14cc/go.mod h1:aYMfkZ6DWSJPJ6c4Wwz3QtW22G7mf/PEgaB9k/ik5+Y=
299 -github.com/shurcooL/httpfs v0.0.0-20171119174359-809beceb2371/go.mod h1:ZY1cvUeJuFPAdZ/B6v7RHavJWZn2YPVFQ1OSXhCGOkg=
300 -github.com/shurcooL/httpgzip v0.0.0-20180522190206-b1c53ac65af9/go.mod h1:919LwcH0M7/W4fcZ0/jy0qGght1GIhqyS/EgWGH2j5Q=
301 -github.com/shurcooL/issues v0.0.0-20181008053335-6292fdc1e191/go.mod h1:e2qWDig5bLteJ4fwvDAc2NHzqFEthkqn7aOZAOpj+PQ=
302 -github.com/shurcooL/issuesapp v0.0.0-20180602232740-048589ce2241/go.mod h1:NPpHK2TI7iSaM0buivtFUc9offApnI0Alt/K8hcHy0I=
303 -github.com/shurcooL/notifications v0.0.0-20181007000457-627ab5aea122/go.mod h1:b5uSkrEVM1jQUspwbixRBhaIjIzL2xazXp6kntxYle0=
304 -github.com/shurcooL/octicon v0.0.0-20181028054416-fa4f57f9efb2/go.mod h1:eWdoE5JD4R5UVWDucdOPg1g2fqQRq78IQa9zlOV1vpQ=
305 -github.com/shurcooL/reactions v0.0.0-20181006231557-f2e0b4ca5b82/go.mod h1:TCR1lToEk4d2s07G3XGfz2QrgHXg4RJBvjrOozvoWfk=
306 -github.com/shurcooL/sanitized_anchor_name v0.0.0-20170918181015-86672fcb3f95/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc=
307 -github.com/shurcooL/users v0.0.0-20180125191416-49c67e49c537/go.mod h1:QJTqeLYEDaXHZDBsXlPCDqdhQuJkuw4NOtaxYe3xii4=
308 -github.com/shurcooL/webdavfs v0.0.0-20170829043945-18c3829fa133/go.mod h1:hKmq5kWdCj2z2KEozexVbfEZIWiTjhE0+UjmZgPqehw=
309 -github.com/sourcegraph/annotate v0.0.0-20160123013949-f4cad6c6324d/go.mod h1:UdhH50NIW0fCiwBSr0co2m7BnFLdv4fQTgdqdJTHFeE=
310 -github.com/sourcegraph/syntaxhighlight v0.0.0-20170531221838-bd320f5d308e/go.mod h1:HuIsMU8RRBOtsCgI77wP899iHVBQpCmg4ErYMZB+2IA=
219 github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI=
220 github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
221 github.com/spf13/cobra v1.10.1 h1:lJeBwCfmrnXthfAupyUTzJ/J4Nc1RsHC/mSRU2dll/s=
222 github.com/spf13/cobra v1.10.1/go.mod h1:7SmJGaTHFVBY0jW4NXGluQoLvhqFQM+6XSKD+P4XaB0=
223 github.com/spf13/pflag v1.0.9 h1:9exaQaMOCwffKiiiYk6/BndUBv+iRViNW+4lEMi0PvY=
224 github.com/spf13/pflag v1.0.9/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
317 -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
318 -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
319 -github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo=
320 -github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
321 -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
322 -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU=
323 -github.com/stretchr/testify v1.8.3/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
324 -github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
225 github.com/stretchr/testify v1.10.0 h1:Xv5erBjTwe/5IxqUQTdXv5kgmIvbHo3QQyRwhJsOfJA=
226 github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
327 -github.com/tarm/serial v0.0.0-20180830185346-98f6abe2eb07/go.mod h1:kDXzergiv9cbyO7IOYJZWg1U88JhDg3PB6klq9Hg2pA=
328 -github.com/viant/assertly v0.4.8/go.mod h1:aGifi++jvCrUaklKEKT0BU95igDNaqkvz+49uaYMPRU=
329 -github.com/viant/toolbox v0.24.0/go.mod h1:OxMCG57V0PXuIP2HNQrtJf2CjqdmbrOx5EkMILuUhzM=
330 -github.com/wlynxg/anet v0.0.3/go.mod h1:eay5PRQr7fIVAMbTbchTnO9gG65Hg/uYGdc7mguHxoA=
227 +github.com/valyala/bytebufferpool v1.0.0 h1:GqA5TC/0021Y/b9FG4Oi9Mr3q7XYx6KllzawFIhcdPw=
228 +github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc=
229 github.com/wlynxg/anet v0.0.5 h1:J3VJGi1gvo0JwZ/P1/Yc/8p63SoW98B5dHkYDmpgvvU=
230 github.com/wlynxg/anet v0.0.5/go.mod h1:eay5PRQr7fIVAMbTbchTnO9gG65Hg/uYGdc7mguHxoA=
231 github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
232 github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
335 -github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
336 -go.opencensus.io v0.18.0/go.mod h1:vKdFvxhtzZ9onBp9VKHK8z/sRpBMnKAsufL7wlDrCOA=
233 go.uber.org/dig v1.19.0 h1:BACLhebsYdpQ7IROQ1AGPjrXcP5dF80U3gKoFzbaq/4=
234 go.uber.org/dig v1.19.0/go.mod h1:Us0rSJiThwCv2GteUN0Q7OKvU7n5J4dxZ9JKUXozFdE=
235 go.uber.org/fx v1.24.0 h1:wE8mruvpg2kiiL1Vqd0CC+tr0/24XIB10Iwp2lLWzkg=
@@ -346,164 +242,57 @@ go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0=
242 go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y=
243 go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8=
244 go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E=
349 -go4.org v0.0.0-20180809161055-417644f6feb5/go.mod h1:MkTOUMDaeVYJUOUsaDXIhWPZYa1yOyC1qaOBpL57BhE=
350 -golang.org/x/build v0.0.0-20190111050920-041ab4dc3f9d/go.mod h1:OWs+y06UdEOHN4y+MfF/py+xQ/tYqIWW03b70/CG9Rw=
351 -golang.org/x/crypto v0.0.0-20181030102418-4d3f4d9ffa16/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
245 golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
353 -golang.org/x/crypto v0.0.0-20190313024323-a1f597ede03a/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
246 golang.org/x/crypto v0.0.0-20190611184440-5c40567a22f8/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
247 golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
356 -golang.org/x/crypto v0.0.0-20200602180216-279210d13fed/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
248 golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
358 -golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4=
359 -golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
360 -golang.org/x/crypto v0.8.0/go.mod h1:mRqEX+O9/h5TFCrQhkgjo2yKi0yYA+9ecGkdQoHrywE=
361 -golang.org/x/crypto v0.12.0/go.mod h1:NF0Gs7EO5K4qLn+Ylc+fih8BSTeIjAP05siRnAh98yw=
362 -golang.org/x/crypto v0.18.0/go.mod h1:R0j02AL6hcrfOiy9T4ZYp/rcWeMxM3L6QYxlOuEG1mg=
249 golang.org/x/crypto v0.41.0 h1:WKYxWedPGCTVVl5+WHSSrOBT0O8lx32+zxmHxijgXp4=
250 golang.org/x/crypto v0.41.0/go.mod h1:pO5AFd7FA68rFak7rOAGVuygIISepHftHnr8dr6+sUc=
365 -golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
251 golang.org/x/exp v0.0.0-20250606033433-dcc06ee1d476 h1:bsqhLWFR6G6xiQcb+JoGqdKdRU6WzPWmK8E0jxTjzo4=
252 golang.org/x/exp v0.0.0-20250606033433-dcc06ee1d476/go.mod h1:3//PLf8L/X+8b4vuAfHzxeRUl04Adcb341+IGKfnqS8=
368 -golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
369 -golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
370 -golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU=
253 golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
254 golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
373 -golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
374 -golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
255 golang.org/x/mod v0.27.0 h1:kb+q2PyFnEADO2IEF935ehFUXlWiNjJWtRNgBLSfbxQ=
256 golang.org/x/mod v0.27.0/go.mod h1:rWI627Fq0DEoudcK+MBkNkCe0EetEaDSwJJkCcjpazc=
377 -golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
378 -golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
379 -golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
380 -golang.org/x/net v0.0.0-20181029044818-c44066c5c816/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
381 -golang.org/x/net v0.0.0-20181106065722-10aee1819953/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
382 -golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
383 -golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
384 -golang.org/x/net v0.0.0-20190313220215-9f648a60d977/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
257 golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
258 golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
259 golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
260 golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
389 -golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
390 -golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
391 -golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
392 -golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
393 -golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns=
394 -golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
395 -golang.org/x/net v0.14.0/go.mod h1:PpSgVXXLK0OxS0F31C1/tv6XNguvCrnXIDrFMspZIUI=
396 -golang.org/x/net v0.20.0/go.mod h1:z8BVo6PvndSri0LbOE3hAn0apkU+1YvI6E70E9jsnvY=
261 golang.org/x/net v0.43.0 h1:lat02VYK2j4aLzMzecihNvTlJNQUq316m2Mr9rnM6YE=
262 golang.org/x/net v0.43.0/go.mod h1:vhO1fvI4dGsIjh73sWfUVjj3N7CA9WkKJNQm2svM6Jg=
399 -golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
400 -golang.org/x/oauth2 v0.0.0-20181017192945-9dcd33a902f4/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
401 -golang.org/x/oauth2 v0.0.0-20181203162652-d668ce993890/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
402 -golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
403 -golang.org/x/perf v0.0.0-20180704124530-6e6d33e29852/go.mod h1:JLpeXjPJfIyPr5TlbXLkXWLhP8nz10XfvxElABhCtcw=
404 -golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
405 -golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
406 -golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
407 -golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
263 golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
264 golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
265 golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
411 -golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
412 -golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
413 -golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
266 golang.org/x/sync v0.16.0 h1:ycBJEhp9p4vXvUZNszeOq0kGTPghopOL8q0fq3vstxw=
267 golang.org/x/sync v0.16.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
416 -golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
417 -golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
418 -golang.org/x/sys v0.0.0-20181029174526-d69651ed3497/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
268 golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
420 -golang.org/x/sys v0.0.0-20190316082340-a2f829d7f35f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
269 golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
422 -golang.org/x/sys v0.0.0-20200602225109-6fdc65e7d980/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
270 golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
424 -golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
425 -golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
426 -golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
427 -golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
271 golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
429 -golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
272 golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
431 -golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
432 -golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
433 -golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
273 golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
435 -golang.org/x/sys v0.16.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
274 golang.org/x/sys v0.35.0 h1:vz1N37gP5bs89s7He8XuIYXpyY0+QlsKmzipCbUtyxI=
275 golang.org/x/sys v0.35.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k=
438 -golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
439 -golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
440 -golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k=
441 -golang.org/x/term v0.7.0/go.mod h1:P32HKFT3hSsZrRxla30E9HqToFYAQPCMs/zFMBUFqPY=
442 -golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo=
443 -golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU=
444 -golang.org/x/term v0.16.0/go.mod h1:yn7UURbUtPyrVJPGPq404EukNFxcm/foM+bV/bfcDsY=
276 golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
446 -golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
277 golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
448 -golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
449 -golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
450 -golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
451 -golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
452 -golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
278 golang.org/x/text v0.28.0 h1:rhazDwis8INMIwQ4tpjLDzUhx6RlXqZNPEM0huQojng=
279 golang.org/x/text v0.28.0/go.mod h1:U8nCwOR8jO/marOQ0QbDiOngZVEBB7MAiitBuMjXiNU=
455 -golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
456 -golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
280 golang.org/x/time v0.12.0 h1:ScB/8o8olJvc+CQPWrK3fPZNfh7qgwCrY0zJmoEQLSE=
281 golang.org/x/time v0.12.0/go.mod h1:CDIdPxbZBQxdj6cxyCIdrNogrJKMJ7pr37NYpMcMDSg=
459 -golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
282 golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
461 -golang.org/x/tools v0.0.0-20181030000716-a0a13e073c7b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
462 -golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
463 -golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
283 golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
284 golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE=
285 golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
467 -golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
468 -golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU=
286 golang.org/x/tools v0.36.0 h1:kWS0uv/zsvHEle1LbV5LE8QujrxB3wfQyxHfhOk0Qkg=
287 golang.org/x/tools v0.36.0/go.mod h1:WBDiHKJK8YgLHlcQPYQzNCkUxUypCaa5ZegCVutKm+s=
288 golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
289 golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
290 golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
291 golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
475 -google.golang.org/api v0.0.0-20180910000450-7ca32eb868bf/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
476 -google.golang.org/api v0.0.0-20181030000543-1d582fd0359e/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
477 -google.golang.org/api v0.1.0/go.mod h1:UGEZY7KEX120AnNLIHFMKIo4obdJhkp2tPbaPlQx13Y=
478 -google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
479 -google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
480 -google.golang.org/appengine v1.3.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
481 -google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
482 -google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
483 -google.golang.org/genproto v0.0.0-20180831171423-11092d34479b/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
484 -google.golang.org/genproto v0.0.0-20181029155118-b69ba1387ce2/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
485 -google.golang.org/genproto v0.0.0-20181202183823-bd91e49a0898/go.mod h1:7Ep/1NZk928CDR8SjdVbjWNpdIf6nzjE3BTgJDr2Atg=
486 -google.golang.org/genproto v0.0.0-20190306203927-b5d61aea6440/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE=
487 -google.golang.org/grpc v1.14.0/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw=
488 -google.golang.org/grpc v1.16.0/go.mod h1:0JHn/cJsOMiMfNA9+DeHDlAU7KAAB5GDlYFpa9MZMio=
489 -google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
490 -google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
292 google.golang.org/protobuf v1.36.6 h1:z1NpPI8ku2WgiWnf+t9wTPsn6eP1L7ksHUlkfLvd9xY=
293 google.golang.org/protobuf v1.36.6/go.mod h1:jduwjTPXsFjZGTmRluh+L6NjiWu7pchiJ2/5YcXBHnY=
294 gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
494 -gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
495 -gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
496 -gopkg.in/inf.v0 v0.9.1/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw=
497 -gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
498 -gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
499 -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
295 gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
296 gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
502 -grpc.go4.org v0.0.0-20170609214715-11d0a25b4919/go.mod h1:77eQGdRu53HpSqPFJFmuJdjuHRquDANNeA4x7B8WQ9o=
503 -honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
504 -honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
505 -honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
297 lukechampine.com/blake3 v1.4.1 h1:I3Smz7gso8w4/TunLKec6K2fn+kyKtDxr/xcQEN84Wg=
298 lukechampine.com/blake3 v1.4.1/go.mod h1:QFosUxmjB8mnrWFSNwKmvxHpfY72bmD2tQ0kBMM3kwo=
508 -sourcegraph.com/sourcegraph/go-diff v0.5.0/go.mod h1:kuch7UrkMzY0X+p9CRK03kfuPQ2zzQcaEFbx8wA8rck=
509 -sourcegraph.com/sqs/pbtypes v0.0.0-20180604144634-d3ebe8f20ae4/go.mod h1:ketZ/q3QxT9HOBeFhu6RdvsftgpsbFHBF5Cas6cDKZ0=
relaydns/core/cryptoops/handshaker.go new
+547
@@ -0,0 +1,547 @@
1 +package cryptoops
2 +
3 +import (
4 + "crypto/cipher"
5 + "crypto/ed25519"
6 + "crypto/rand"
7 + "crypto/sha256"
8 + "errors"
9 + "fmt"
10 + "io"
11 + "time"
12 +
13 + "golang.org/x/crypto/chacha20poly1305"
14 + "golang.org/x/crypto/curve25519"
15 + "golang.org/x/crypto/hkdf"
16 + "google.golang.org/protobuf/proto"
17 +
18 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
19 +)
20 +
21 +var (
22 + ErrHandshakeFailed = errors.New("handshake failed")
23 + ErrInvalidSignature = errors.New("invalid signature")
24 + ErrInvalidTimestamp = errors.New("invalid timestamp")
25 + ErrInvalidProtocol = errors.New("invalid protocol version")
26 + ErrInvalidIdentity = errors.New("invalid identity")
27 + ErrSessionKeyDerive = errors.New("failed to derive session key")
28 + ErrEncryptionFailed = errors.New("encryption failed")
29 + ErrDecryptionFailed = errors.New("decryption failed")
30 + ErrInvalidNonce = errors.New("invalid nonce")
31 +)
32 +
33 +const (
34 + nonceSize = 12 // ChaCha20Poly1305 nonce size
35 + sessionKeySize = 32 // X25519 shared secret size
36 + maxTimestampSkew = 30 * time.Second
37 + maxRawPacketSize = 1 << 26 // 64MB - same as relay server
38 +
39 + // HKDF info strings for key derivation
40 + clientKeyInfo = "RDSEC_KEY_CLIENT"
41 + serverKeyInfo = "RDSEC_KEY_SERVER"
42 +)
43 +
44 +// Handshaker handles the X25519-ChaCha20Poly1305 based handshake protocol
45 +type Handshaker struct {
46 + credential *Credential
47 +}
48 +
49 +// NewHandshaker creates a new Handshaker with the given credential
50 +func NewHandshaker(credential *Credential) *Handshaker {
51 + return &Handshaker{
52 + credential: credential,
53 + }
54 +}
55 +
56 +// SecureConnection represents a secured connection with encryption capabilities
57 +type SecureConnection struct {
58 + conn io.ReadWriteCloser
59 + encryptor cipher.AEAD
60 + decryptor cipher.AEAD
61 + encryptNonce []byte
62 + decryptNonce []byte
63 +}
64 +
65 +// Write encrypts and writes data to the underlying connection
66 +func (sc *SecureConnection) Write(p []byte) (int, error) {
67 + // Increment nonce for each message
68 + incrementNonce(sc.encryptNonce)
69 +
70 + // Encrypt the data
71 + encrypted := sc.encryptor.Seal(nil, sc.encryptNonce, p, nil)
72 +
73 + // Create EncryptedData message
74 + encryptedData := &rdsec.EncryptedData{
75 + Nonce: make([]byte, len(sc.encryptNonce)),
76 + Payload: encrypted,
77 + }
78 + copy(encryptedData.Nonce, sc.encryptNonce)
79 +
80 + // Serialize and send
81 + data, err := proto.Marshal(encryptedData)
82 + if err != nil {
83 + return 0, ErrEncryptionFailed
84 + }
85 +
86 + // Check packet size limit
87 + if len(data) > maxRawPacketSize {
88 + return 0, ErrEncryptionFailed
89 + }
90 +
91 + // Write length-prefixed message
92 + if err := writeLengthPrefixed(sc.conn, data); err != nil {
93 + return 0, err
94 + }
95 +
96 + return len(p), nil
97 +}
98 +
99 +// Read reads and decrypts data from the underlying connection
100 +func (sc *SecureConnection) Read(p []byte) (int, error) {
101 + // Read the encrypted data message
102 + encryptedData := &rdsec.EncryptedData{}
103 +
104 + // Read length prefix first (4 bytes)
105 + lengthBuf := make([]byte, 4)
106 + _, err := io.ReadFull(sc.conn, lengthBuf)
107 + if err != nil {
108 + return 0, err
109 + }
110 +
111 + // Calculate message length
112 + length := int(lengthBuf[0])<<24 | int(lengthBuf[1])<<16 | int(lengthBuf[2])<<8 | int(lengthBuf[3])
113 +
114 + // Check packet size limit
115 + if length > maxRawPacketSize {
116 + return 0, ErrDecryptionFailed
117 + }
118 +
119 + // Read the message
120 + msgBuf := make([]byte, length)
121 + _, err = io.ReadFull(sc.conn, msgBuf)
122 + if err != nil {
123 + return 0, err
124 + }
125 +
126 + // Unmarshal the message
127 + err = proto.Unmarshal(msgBuf, encryptedData)
128 + if err != nil {
129 + return 0, ErrDecryptionFailed
130 + }
131 +
132 + // Validate nonce
133 + if len(encryptedData.Nonce) != nonceSize {
134 + return 0, ErrInvalidNonce
135 + }
136 +
137 + // Decrypt the data
138 + decrypted, err := sc.decryptor.Open(nil, encryptedData.Nonce, encryptedData.Payload, nil)
139 + if err != nil {
140 + return 0, ErrDecryptionFailed
141 + }
142 +
143 + // Copy decrypted data to the provided buffer
144 + copy(p, decrypted)
145 + return len(decrypted), nil
146 +}
147 +
148 +// Close closes the underlying connection
149 +func (sc *SecureConnection) Close() error {
150 + return sc.conn.Close()
151 +}
152 +
153 +// ClientHandshake performs the client-side of the handshake
154 +func (h *Handshaker) ClientHandshake(conn io.ReadWriteCloser, alpn string) (*SecureConnection, error) {
155 + // Generate ephemeral key pair for this session
156 + ephemeralPriv, ephemeralPub, err := generateX25519KeyPair()
157 + if err != nil {
158 + return nil, ErrHandshakeFailed
159 + }
160 +
161 + // Create client init message
162 + timestamp := time.Now().Unix()
163 + nonce := make([]byte, nonceSize)
164 + if _, err := rand.Read(nonce); err != nil {
165 + return nil, ErrHandshakeFailed
166 + }
167 +
168 + clientInitPayload := &rdsec.ClientInitPayload{
169 + Version: rdsec.ProtocolVersion_PROTOCOL_VERSION_1,
170 + Nonce: nonce,
171 + Timestamp: timestamp,
172 + Identity: &rdsec.Identity{
173 + Id: h.credential.ID(),
174 + PublicKey: h.credential.PublicKey(),
175 + },
176 + Alpn: alpn,
177 + SessionPublicKey: ephemeralPub,
178 + }
179 +
180 + // Serialize and sign the payload
181 + payloadBytes, err := proto.Marshal(clientInitPayload)
182 + if err != nil {
183 + return nil, ErrHandshakeFailed
184 + }
185 +
186 + signature := h.credential.Sign(payloadBytes)
187 +
188 + clientInit := &rdsec.SignedPayload{
189 + Data: payloadBytes,
190 + Signature: signature,
191 + }
192 +
193 + // Send client init message
194 + clientInitBytes, err := proto.Marshal(clientInit)
195 + if err != nil {
196 + return nil, ErrHandshakeFailed
197 + }
198 +
199 + // Write length-prefixed message
200 + if err := writeLengthPrefixed(conn, clientInitBytes); err != nil {
201 + return nil, ErrHandshakeFailed
202 + }
203 +
204 + // Read server init response
205 + serverInitBytes, err := readLengthPrefixed(conn)
206 + if err != nil {
207 + return nil, ErrHandshakeFailed
208 + }
209 +
210 + serverInitSigned := &rdsec.SignedPayload{}
211 + if err := proto.Unmarshal(serverInitBytes, serverInitSigned); err != nil {
212 + return nil, ErrHandshakeFailed
213 + }
214 +
215 + // Unmarshal the server init payload
216 + serverInitPayload := &rdsec.ServerInitPayload{}
217 + if err := proto.Unmarshal(serverInitSigned.GetData(), serverInitPayload); err != nil {
218 + return nil, ErrHandshakeFailed
219 + }
220 +
221 + // Validate server init
222 + if err := h.validateServerInit(serverInitSigned, serverInitPayload); err != nil {
223 + return nil, err
224 + }
225 +
226 + // Derive session keys
227 + clientEncryptKey, clientDecryptKey, err := h.deriveClientSessionKeys(
228 + ephemeralPriv, ephemeralPub, serverInitPayload.GetSessionPublicKey(),
229 + clientInitPayload.GetNonce(), serverInitPayload.GetNonce(),
230 + )
231 + if err != nil {
232 + return nil, err
233 + }
234 +
235 + // Create secure connection
236 + return h.createSecureConnection(conn, clientEncryptKey, clientDecryptKey, nonce, serverInitPayload.GetNonce())
237 +}
238 +
239 +// ServerHandshake performs the server-side of the handshake
240 +func (h *Handshaker) ServerHandshake(conn io.ReadWriteCloser, alpn string) (*SecureConnection, error) {
241 + // Read client init message
242 + clientInitBytes, err := readLengthPrefixed(conn)
243 + if err != nil {
244 + return nil, ErrHandshakeFailed
245 + }
246 +
247 + clientInitSigned := &rdsec.SignedPayload{}
248 + if err := proto.Unmarshal(clientInitBytes, clientInitSigned); err != nil {
249 + return nil, ErrHandshakeFailed
250 + }
251 +
252 + // Unmarshal the client init payload
253 + clientInitPayload := &rdsec.ClientInitPayload{}
254 + if err := proto.Unmarshal(clientInitSigned.GetData(), clientInitPayload); err != nil {
255 + return nil, ErrHandshakeFailed
256 + }
257 +
258 + // Validate client init
259 + if err := h.validateClientInit(clientInitSigned, clientInitPayload, alpn); err != nil {
260 + // Silent failure: close connection and return error without sending response
261 + conn.Close()
262 + return nil, err
263 + }
264 +
265 + // Generate ephemeral key pair for this session
266 + ephemeralPriv, ephemeralPub, err := generateX25519KeyPair()
267 + if err != nil {
268 + return nil, ErrHandshakeFailed
269 + }
270 +
271 + // Create server init message
272 + timestamp := time.Now().Unix()
273 + nonce := make([]byte, nonceSize)
274 + if _, err := rand.Read(nonce); err != nil {
275 + return nil, ErrHandshakeFailed
276 + }
277 +
278 + serverInitPayload := &rdsec.ServerInitPayload{
279 + Version: rdsec.ProtocolVersion_PROTOCOL_VERSION_1,
280 + Nonce: nonce,
281 + Timestamp: timestamp,
282 + Identity: &rdsec.Identity{
283 + Id: h.credential.ID(),
284 + PublicKey: h.credential.PublicKey(),
285 + },
286 + Alpn: alpn,
287 + SessionPublicKey: ephemeralPub,
288 + }
289 +
290 + // Serialize and sign the payload
291 + payloadBytes, err := proto.Marshal(serverInitPayload)
292 + if err != nil {
293 + return nil, ErrHandshakeFailed
294 + }
295 +
296 + signature := h.credential.Sign(payloadBytes)
297 +
298 + serverInit := &rdsec.SignedPayload{
299 + Data: payloadBytes,
300 + Signature: signature,
301 + }
302 +
303 + // Derive session keys
304 + serverEncryptKey, serverDecryptKey, err := h.deriveServerSessionKeys(
305 + ephemeralPriv, ephemeralPub, clientInitPayload.GetSessionPublicKey(),
306 + clientInitPayload.GetNonce(), nonce,
307 + )
308 + if err != nil {
309 + return nil, err
310 + }
311 +
312 + // Send server init message
313 + serverInitBytes, err := proto.Marshal(serverInit)
314 + if err != nil {
315 + return nil, ErrHandshakeFailed
316 + }
317 +
318 + // Write length-prefixed message
319 + if err := writeLengthPrefixed(conn, serverInitBytes); err != nil {
320 + return nil, ErrHandshakeFailed
321 + }
322 +
323 + // Create secure connection
324 + return h.createSecureConnection(conn, serverEncryptKey, serverDecryptKey, nonce, clientInitPayload.GetNonce())
325 +}
326 +
327 +// validateClientInit validates the client init message
328 +func (h *Handshaker) validateClientInit(clientInitSigned *rdsec.SignedPayload, clientInitPayload *rdsec.ClientInitPayload, expectedAlpn string) error {
329 + if clientInitSigned == nil || clientInitPayload == nil {
330 + return ErrInvalidProtocol
331 + }
332 +
333 + // Check protocol version
334 + if clientInitPayload.GetVersion() != rdsec.ProtocolVersion_PROTOCOL_VERSION_1 {
335 + return ErrInvalidProtocol
336 + }
337 +
338 + // Check timestamp
339 + if err := validateTimestamp(clientInitPayload.GetTimestamp()); err != nil {
340 + return err
341 + }
342 +
343 + // Check ALPN
344 + if clientInitPayload.GetAlpn() != expectedAlpn {
345 + return ErrHandshakeFailed
346 + }
347 +
348 + // Validate identity
349 + if !ValidateIdentity(clientInitPayload.GetIdentity()) {
350 + return ErrInvalidIdentity
351 + }
352 +
353 + // Verify signature
354 + if !ed25519.Verify(clientInitPayload.GetIdentity().GetPublicKey(), clientInitSigned.GetData(), clientInitSigned.GetSignature()) {
355 + return ErrInvalidSignature
356 + }
357 +
358 + return nil
359 +}
360 +
361 +// validateServerInit validates the server init message
362 +func (h *Handshaker) validateServerInit(serverInitSigned *rdsec.SignedPayload, serverInitPayload *rdsec.ServerInitPayload) error {
363 + if serverInitSigned == nil || serverInitPayload == nil {
364 + return ErrInvalidProtocol
365 + }
366 +
367 + // Check protocol version
368 + if serverInitPayload.GetVersion() != rdsec.ProtocolVersion_PROTOCOL_VERSION_1 {
369 + return ErrInvalidProtocol
370 + }
371 +
372 + // Check timestamp
373 + if err := validateTimestamp(serverInitPayload.GetTimestamp()); err != nil {
374 + return err
375 + }
376 +
377 + // Validate identity
378 + if !ValidateIdentity(serverInitPayload.GetIdentity()) {
379 + return ErrInvalidIdentity
380 + }
381 +
382 + // Verify signature
383 + if !ed25519.Verify(serverInitPayload.GetIdentity().GetPublicKey(), serverInitSigned.GetData(), serverInitSigned.GetSignature()) {
384 + return ErrInvalidSignature
385 + }
386 +
387 + return nil
388 +}
389 +
390 +// deriveClientSessionKeys derives encryption and decryption keys for the client
391 +func (h *Handshaker) deriveClientSessionKeys(clientPriv, clientPub, serverPub, clientNonce, serverNonce []byte) ([]byte, []byte, error) {
392 + // Compute shared secret
393 + sharedSecret, err := curve25519.X25519(clientPriv, serverPub)
394 + if err != nil {
395 + return nil, nil, ErrSessionKeyDerive
396 + }
397 +
398 + // Derive keys using HKDF-like construction
399 + // Both client and server use the same derivation for the same direction
400 + // Client encrypts, server decrypts
401 + salt := append(clientNonce, serverNonce...)
402 + encryptKey := deriveKey(sharedSecret, salt, []byte(clientKeyInfo))
403 + // Server encrypts, client decrypts
404 + salt = append(serverNonce, clientNonce...)
405 + decryptKey := deriveKey(sharedSecret, salt, []byte(serverKeyInfo))
406 +
407 + return encryptKey, decryptKey, nil
408 +}
409 +
410 +// deriveServerSessionKeys derives encryption and decryption keys for the server
411 +func (h *Handshaker) deriveServerSessionKeys(serverPriv, serverPub, clientPub, clientNonce, serverNonce []byte) ([]byte, []byte, error) {
412 + // Compute shared secret (should be same as client's)
413 + sharedSecret, err := curve25519.X25519(serverPriv, clientPub)
414 + if err != nil {
415 + return nil, nil, ErrSessionKeyDerive
416 + }
417 +
418 + // Derive keys using HKDF-like construction
419 + // Both client and server use the same derivation for the same direction
420 + // Server encrypts, client decrypts
421 + salt := append(serverNonce, clientNonce...)
422 + encryptKey := deriveKey(sharedSecret, salt, []byte(serverKeyInfo))
423 + // Client encrypts, server decrypts
424 + salt = append(clientNonce, serverNonce...)
425 + decryptKey := deriveKey(sharedSecret, salt, []byte(clientKeyInfo))
426 +
427 + return encryptKey, decryptKey, nil
428 +}
429 +
430 +// createSecureConnection creates a new SecureConnection with the given keys and nonces
431 +func (h *Handshaker) createSecureConnection(conn io.ReadWriteCloser, encryptKey, decryptKey, encryptNonce, decryptNonce []byte) (*SecureConnection, error) {
432 + // Create AEAD instances
433 + encryptor, err := chacha20poly1305.New(encryptKey)
434 + if err != nil {
435 + return nil, ErrEncryptionFailed
436 + }
437 +
438 + decryptor, err := chacha20poly1305.New(decryptKey)
439 + if err != nil {
440 + return nil, ErrEncryptionFailed
441 + }
442 +
443 + // Copy nonces to avoid modifying the originals
444 + encNonce := make([]byte, nonceSize)
445 + decNonce := make([]byte, nonceSize)
446 + copy(encNonce, encryptNonce)
447 + copy(decNonce, decryptNonce)
448 +
449 + return &SecureConnection{
450 + conn: conn,
451 + encryptor: encryptor,
452 + decryptor: decryptor,
453 + encryptNonce: encNonce,
454 + decryptNonce: decNonce,
455 + }, nil
456 +}
457 +
458 +// Helper functions
459 +
460 +// generateX25519KeyPair generates a new X25519 key pair
461 +func generateX25519KeyPair() ([]byte, []byte, error) {
462 + priv := make([]byte, curve25519.ScalarSize)
463 + if _, err := rand.Read(priv); err != nil {
464 + return nil, nil, err
465 + }
466 +
467 + pub, err := curve25519.X25519(priv, curve25519.Basepoint)
468 + if err != nil {
469 + return nil, nil, err
470 + }
471 +
472 + return priv, pub, nil
473 +}
474 +
475 +// deriveKey derives a key from the shared secret using HKDF-SHA256
476 +func deriveKey(sharedSecret, salt, info []byte) []byte {
477 + hkdf := hkdf.New(sha256.New, sharedSecret, salt, info)
478 + key := make([]byte, sessionKeySize)
479 + if _, err := hkdf.Read(key); err != nil {
480 + // HKDF should never fail with valid inputs, treat as critical error
481 + panic(fmt.Sprintf("HKDF key derivation failed: %v", err))
482 + }
483 + return key
484 +}
485 +
486 +// validateTimestamp validates that the timestamp is within acceptable range
487 +func validateTimestamp(timestamp int64) error {
488 + now := time.Now().Unix()
489 + diff := now - timestamp
490 +
491 + if diff < -int64(maxTimestampSkew.Seconds()) || diff > int64(maxTimestampSkew.Seconds()) {
492 + return ErrInvalidTimestamp
493 + }
494 +
495 + return nil
496 +}
497 +
498 +// incrementNonce increments the nonce for the next message
499 +func incrementNonce(nonce []byte) {
500 + // Simple increment - in production, you might want a more sophisticated approach
501 + for i := len(nonce) - 1; i >= 0; i-- {
502 + nonce[i]++
503 + if nonce[i] != 0 {
504 + break
505 + }
506 + }
507 +}
508 +
509 +// writeLengthPrefixed writes a length-prefixed message to the connection
510 +func writeLengthPrefixed(conn io.Writer, data []byte) error {
511 + length := len(data)
512 + lengthBytes := []byte{
513 + byte(length >> 24),
514 + byte(length >> 16),
515 + byte(length >> 8),
516 + byte(length),
517 + }
518 +
519 + if _, err := conn.Write(lengthBytes); err != nil {
520 + return err
521 + }
522 +
523 + _, err := conn.Write(data)
524 + return err
525 +}
526 +
527 +// readLengthPrefixed reads a length-prefixed message from the connection
528 +func readLengthPrefixed(conn io.Reader) ([]byte, error) {
529 + lengthBytes := make([]byte, 4)
530 + if _, err := io.ReadFull(conn, lengthBytes); err != nil {
531 + return nil, err
532 + }
533 +
534 + length := int(lengthBytes[0])<<24 | int(lengthBytes[1])<<16 | int(lengthBytes[2])<<8 | int(lengthBytes[3])
535 +
536 + // Check packet size limit
537 + if length > maxRawPacketSize {
538 + return nil, ErrHandshakeFailed
539 + }
540 +
541 + data := make([]byte, length)
542 + if _, err := io.ReadFull(conn, data); err != nil {
543 + return nil, err
544 + }
545 +
546 + return data, nil
547 +}
relaydns/core/cryptoops/handshaker_test.go new
+358
@@ -0,0 +1,358 @@
1 +package cryptoops
2 +
3 +import (
4 + "bytes"
5 + "crypto/ed25519"
6 + "crypto/rand"
7 + "io"
8 + "testing"
9 + "time"
10 +
11 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
12 +)
13 +
14 +// pipeConn implements a connection using io.Pipe for bidirectional communication
15 +type pipeConn struct {
16 + reader io.Reader
17 + writer io.Writer
18 + closed bool
19 +}
20 +
21 +func (c *pipeConn) Read(p []byte) (n int, err error) {
22 + if c.closed {
23 + return 0, io.EOF
24 + }
25 + return c.reader.Read(p)
26 +}
27 +
28 +func (c *pipeConn) Write(p []byte) (n int, err error) {
29 + if c.closed {
30 + return 0, io.ErrClosedPipe
31 + }
32 + return c.writer.Write(p)
33 +}
34 +
35 +func (c *pipeConn) Close() error {
36 + c.closed = true
37 + // Try to close both reader and writer if they support it
38 + if closer, ok := c.reader.(io.Closer); ok {
39 + closer.Close()
40 + }
41 + if closer, ok := c.writer.(io.Closer); ok {
42 + closer.Close()
43 + }
44 + return nil
45 +}
46 +
47 +// TestHandshake tests the full handshake process between client and server
48 +func TestHandshake(t *testing.T) {
49 + // Create credentials for client and server
50 + clientCred, err := NewCredential()
51 + if err != nil {
52 + t.Fatalf("Failed to create client credential: %v", err)
53 + }
54 +
55 + serverCred, err := NewCredential()
56 + if err != nil {
57 + t.Fatalf("Failed to create server credential: %v", err)
58 + }
59 +
60 + // Create handshakers
61 + clientHandshaker := NewHandshaker(clientCred)
62 + serverHandshaker := NewHandshaker(serverCred)
63 +
64 + // Create a pipe for bidirectional communication
65 + clientReader, clientWriter := io.Pipe()
66 + serverReader, serverWriter := io.Pipe()
67 +
68 + // Create pipe connections
69 + clientPipeConn := &pipeConn{
70 + reader: clientReader,
71 + writer: serverWriter,
72 + }
73 + serverPipeConn := &pipeConn{
74 + reader: serverReader,
75 + writer: clientWriter,
76 + }
77 +
78 + alpn := "test-alpn"
79 +
80 + // Use channels to coordinate
81 + done := make(chan bool, 2)
82 + var clientSecureConn, serverSecureConn *SecureConnection
83 + var clientErr, serverErr error
84 +
85 + // Start server handshake in a goroutine
86 + go func() {
87 + defer func() { done <- true }()
88 + serverSecureConn, serverErr = serverHandshaker.ServerHandshake(serverPipeConn, alpn)
89 + }()
90 +
91 + // Give the server a moment to start waiting
92 + time.Sleep(10 * time.Millisecond)
93 +
94 + // Start client handshake in a goroutine
95 + go func() {
96 + defer func() { done <- true }()
97 + clientSecureConn, clientErr = clientHandshaker.ClientHandshake(clientPipeConn, alpn)
98 + }()
99 +
100 + // Wait for both handshakes to complete
101 + for i := 0; i < 2; i++ {
102 + select {
103 + case <-done:
104 + // One handshake completed
105 + case <-time.After(5 * time.Second):
106 + t.Fatal("Handshake timed out")
107 + }
108 + }
109 +
110 + // Check for errors
111 + if clientErr != nil {
112 + t.Fatalf("Client handshake failed: %v", clientErr)
113 + }
114 + if serverErr != nil {
115 + t.Fatalf("Server handshake failed: %v", serverErr)
116 + }
117 +
118 + // Test encrypted communication
119 + testMessage := []byte("Hello, secure world!")
120 +
121 + // Use channels to coordinate communication
122 + commDone := make(chan bool, 2)
123 +
124 + // Client writes encrypted message
125 + go func() {
126 + defer func() { commDone <- true }()
127 +
128 + n, err := clientSecureConn.Write(testMessage)
129 + if err != nil {
130 + t.Errorf("Client write failed: %v", err)
131 + return
132 + }
133 + if n != len(testMessage) {
134 + t.Errorf("Client wrote %d bytes, expected %d", n, len(testMessage))
135 + }
136 +
137 + // Client reads response
138 + clientReadBuf := make([]byte, 1024)
139 + n, err = clientSecureConn.Read(clientReadBuf)
140 + if err != nil {
141 + t.Errorf("Client read failed: %v", err)
142 + return
143 + }
144 +
145 + responseMessage := []byte("Hello, client!")
146 + receivedResponse := clientReadBuf[:n]
147 + if !bytes.Equal(receivedResponse, responseMessage) {
148 + t.Errorf("Client received %q, expected %q", receivedResponse, responseMessage)
149 + }
150 + }()
151 +
152 + // Server reads and writes response
153 + go func() {
154 + defer func() { commDone <- true }()
155 +
156 + // Server reads and decrypts message
157 + serverReadBuf := make([]byte, 1024)
158 + n, err := serverSecureConn.Read(serverReadBuf)
159 + if err != nil {
160 + t.Errorf("Server read failed: %v", err)
161 + return
162 + }
163 +
164 + receivedMessage := serverReadBuf[:n]
165 + if !bytes.Equal(receivedMessage, testMessage) {
166 + t.Errorf("Server received %q, expected %q", receivedMessage, testMessage)
167 + }
168 +
169 + // Server writes encrypted response
170 + responseMessage := []byte("Hello, client!")
171 + n, err = serverSecureConn.Write(responseMessage)
172 + if err != nil {
173 + t.Errorf("Server write failed: %v", err)
174 + return
175 + }
176 + if n != len(responseMessage) {
177 + t.Errorf("Server wrote %d bytes, expected %d", n, len(responseMessage))
178 + }
179 + }()
180 +
181 + // Wait for both communication operations to complete
182 + for i := 0; i < 2; i++ {
183 + select {
184 + case <-commDone:
185 + // One operation completed
186 + case <-time.After(5 * time.Second):
187 + t.Fatal("Communication timed out")
188 + }
189 + }
190 +
191 + // Close connections
192 + clientSecureConn.Close()
193 + serverSecureConn.Close()
194 +}
195 +
196 +// TestValidateIdentity tests the identity validation function
197 +func TestValidateIdentity(t *testing.T) {
198 + // Create a valid credential
199 + cred, err := NewCredential()
200 + if err != nil {
201 + t.Fatalf("Failed to create credential: %v", err)
202 + }
203 +
204 + // Create a valid identity
205 + validIdentity := &rdsec.Identity{
206 + Id: cred.ID(),
207 + PublicKey: cred.PublicKey(),
208 + }
209 +
210 + if !ValidateIdentity(validIdentity) {
211 + t.Error("Valid identity was rejected")
212 + }
213 +
214 + // Test invalid identity (wrong ID)
215 + invalidIdentity := &rdsec.Identity{
216 + Id: "wrong-id",
217 + PublicKey: cred.PublicKey(),
218 + }
219 +
220 + if ValidateIdentity(invalidIdentity) {
221 + t.Error("Invalid identity was accepted")
222 + }
223 +
224 + // Test invalid identity (wrong public key)
225 + _, wrongPubKey, err := ed25519.GenerateKey(rand.Reader)
226 + if err != nil {
227 + t.Fatalf("Failed to generate wrong public key: %v", err)
228 + }
229 +
230 + invalidIdentity2 := &rdsec.Identity{
231 + Id: cred.ID(),
232 + PublicKey: wrongPubKey,
233 + }
234 +
235 + if ValidateIdentity(invalidIdentity2) {
236 + t.Error("Invalid identity with wrong public key was accepted")
237 + }
238 +}
239 +
240 +// TestCredential tests the credential functions
241 +func TestCredential(t *testing.T) {
242 + // Test creating a new credential
243 + cred, err := NewCredential()
244 + if err != nil {
245 + t.Fatalf("Failed to create credential: %v", err)
246 + }
247 +
248 + // Test ID function
249 + id := cred.ID()
250 + if id == "" {
251 + t.Error("Credential ID is empty")
252 + }
253 +
254 + // Test public key function
255 + pubKey := cred.PublicKey()
256 + if len(pubKey) != ed25519.PublicKeySize {
257 + t.Errorf("Public key size is %d, expected %d", len(pubKey), ed25519.PublicKeySize)
258 + }
259 +
260 + // Test private key function
261 + privKey := cred.PrivateKey()
262 + if len(privKey) != ed25519.PrivateKeySize {
263 + t.Errorf("Private key size is %d, expected %d", len(privKey), ed25519.PrivateKeySize)
264 + }
265 +
266 + // Test sign and verify
267 + message := []byte("test message")
268 + signature := cred.Sign(message)
269 +
270 + if !cred.Verify(message, signature) {
271 + t.Error("Signature verification failed")
272 + }
273 +
274 + // Test verification with wrong message
275 + wrongMessage := []byte("wrong message")
276 + if cred.Verify(wrongMessage, signature) {
277 + t.Error("Signature verification should have failed for wrong message")
278 + }
279 +
280 + // Test verification with wrong signature
281 + wrongSignature := make([]byte, ed25519.SignatureSize)
282 + if cred.Verify(message, wrongSignature) {
283 + t.Error("Signature verification should have failed for wrong signature")
284 + }
285 +}
286 +
287 +// TestHandshakeWithInvalidALPN tests that handshake fails with different ALPNs
288 +func TestHandshakeWithInvalidALPN(t *testing.T) {
289 + // Create credentials for client and server
290 + clientCred, err := NewCredential()
291 + if err != nil {
292 + t.Fatalf("Failed to create client credential: %v", err)
293 + }
294 +
295 + serverCred, err := NewCredential()
296 + if err != nil {
297 + t.Fatalf("Failed to create server credential: %v", err)
298 + }
299 +
300 + // Create handshakers
301 + clientHandshaker := NewHandshaker(clientCred)
302 + serverHandshaker := NewHandshaker(serverCred)
303 +
304 + // Create a pipe for bidirectional communication
305 + clientReader, clientWriter := io.Pipe()
306 + serverReader, serverWriter := io.Pipe()
307 +
308 + // Create pipe connections
309 + clientPipeConn := &pipeConn{
310 + reader: clientReader,
311 + writer: serverWriter,
312 + }
313 + serverPipeConn := &pipeConn{
314 + reader: serverReader,
315 + writer: clientWriter,
316 + }
317 +
318 + // Use different ALPNs
319 + clientALPN := "client-alpn"
320 + serverALPN := "server-alpn"
321 +
322 + // Use channels to coordinate
323 + done := make(chan bool, 2)
324 + var clientErr, serverErr error
325 +
326 + // Start server handshake in a goroutine
327 + go func() {
328 + defer func() { done <- true }()
329 + _, serverErr = serverHandshaker.ServerHandshake(serverPipeConn, serverALPN)
330 + }()
331 +
332 + // Give the server a moment to start waiting
333 + time.Sleep(10 * time.Millisecond)
334 +
335 + // Start client handshake in a goroutine
336 + go func() {
337 + defer func() { done <- true }()
338 + _, clientErr = clientHandshaker.ClientHandshake(clientPipeConn, clientALPN)
339 + }()
340 +
341 + // Wait for both handshakes to complete
342 + for i := 0; i < 2; i++ {
343 + select {
344 + case <-done:
345 + // One handshake completed
346 + case <-time.After(5 * time.Second):
347 + t.Fatal("Handshake timed out")
348 + }
349 + }
350 +
351 + // Check for errors
352 + if clientErr == nil {
353 + t.Error("Client handshake should have failed with different ALPNs")
354 + }
355 + if serverErr == nil {
356 + t.Error("Server handshake should have failed with different ALPNs")
357 + }
358 +}
relaydns/core/cryptoops/identity.go new
+41
@@ -0,0 +1,41 @@
1 +package cryptoops
2 +
3 +import (
4 + "crypto/ed25519"
5 + "errors"
6 +
7 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
8 +)
9 +
10 +func ValidateIdentity(identity *rdsec.Identity) bool {
11 + if identity == nil {
12 + return false
13 + }
14 +
15 + if len(identity.PublicKey) != ed25519.PublicKeySize {
16 + return false
17 + }
18 +
19 + id := DeriveID(identity.PublicKey)
20 +
21 + return id == identity.Id
22 +}
23 +
24 +var (
25 + ErrInvalidMessage = errors.New("invalid message")
26 +)
27 +
28 +func VerifySignedPayload(message *rdsec.SignedPayload, id *rdsec.Identity) bool {
29 + if message == nil {
30 + return false
31 + }
32 + if id == nil {
33 + return false
34 + }
35 +
36 + if !ValidateIdentity(id) {
37 + return false
38 + }
39 +
40 + return ed25519.Verify(id.PublicKey, message.Data, message.Signature)
41 +}
relaydns/core/cryptoops/key_derivation_test.go new
+118
@@ -0,0 +1,118 @@
1 +package cryptoops
2 +
3 +import (
4 + "bytes"
5 + "crypto/rand"
6 + "testing"
7 +
8 + "golang.org/x/crypto/chacha20poly1305"
9 +)
10 +
11 +// TestKeyDerivation tests the key derivation functions
12 +func TestKeyDerivation(t *testing.T) {
13 + // Generate two X25519 key pairs
14 + clientPriv, clientPub, err := generateX25519KeyPair()
15 + if err != nil {
16 + t.Fatalf("Failed to generate client key pair: %v", err)
17 + }
18 +
19 + serverPriv, serverPub, err := generateX25519KeyPair()
20 + if err != nil {
21 + t.Fatalf("Failed to generate server key pair: %v", err)
22 + }
23 +
24 + // Generate nonces
25 + clientNonce := make([]byte, nonceSize)
26 + serverNonce := make([]byte, nonceSize)
27 + if _, err := rand.Read(clientNonce); err != nil {
28 + t.Fatalf("Failed to generate client nonce: %v", err)
29 + }
30 + if _, err := rand.Read(serverNonce); err != nil {
31 + t.Fatalf("Failed to generate server nonce: %v", err)
32 + }
33 +
34 + // Create handshakers
35 + clientCred, err := NewCredential()
36 + if err != nil {
37 + t.Fatalf("Failed to create client credential: %v", err)
38 + }
39 + serverCred, err := NewCredential()
40 + if err != nil {
41 + t.Fatalf("Failed to create server credential: %v", err)
42 + }
43 +
44 + clientHandshaker := NewHandshaker(clientCred)
45 + serverHandshaker := NewHandshaker(serverCred)
46 +
47 + // Derive keys
48 + clientEncryptKey, clientDecryptKey, err := clientHandshaker.deriveClientSessionKeys(
49 + clientPriv, clientPub, serverPub, clientNonce, serverNonce)
50 + if err != nil {
51 + t.Fatalf("Failed to derive client session keys: %v", err)
52 + }
53 +
54 + serverEncryptKey, serverDecryptKey, err := serverHandshaker.deriveServerSessionKeys(
55 + serverPriv, serverPub, clientPub, clientNonce, serverNonce)
56 + if err != nil {
57 + t.Fatalf("Failed to derive server session keys: %v", err)
58 + }
59 +
60 + // Check that keys match correctly
61 + // Client encrypts, server decrypts
62 + if !bytes.Equal(clientEncryptKey, serverDecryptKey) {
63 + t.Error("Client encrypt key doesn't match server decrypt key")
64 + }
65 +
66 + // Server encrypts, client decrypts
67 + if !bytes.Equal(serverEncryptKey, clientDecryptKey) {
68 + t.Error("Server encrypt key doesn't match client decrypt key")
69 + }
70 +
71 + // Test actual encryption/decryption
72 + testMessage := []byte("Hello, world!")
73 +
74 + // Client encrypts
75 + clientAEAD, err := chacha20poly1305.New(clientEncryptKey)
76 + if err != nil {
77 + t.Fatalf("Failed to create client AEAD: %v", err)
78 + }
79 +
80 + clientEncryptNonce := make([]byte, nonceSize)
81 + copy(clientEncryptNonce, clientNonce) // Start with client nonce
82 + encrypted := clientAEAD.Seal(nil, clientEncryptNonce, testMessage, nil)
83 +
84 + // Server decrypts
85 + serverAEAD, err := chacha20poly1305.New(serverDecryptKey)
86 + if err != nil {
87 + t.Fatalf("Failed to create server AEAD: %v", err)
88 + }
89 +
90 + serverDecryptNonce := make([]byte, nonceSize)
91 + copy(serverDecryptNonce, clientNonce) // Use same nonce as client
92 + decrypted, err := serverAEAD.Open(nil, serverDecryptNonce, encrypted, nil)
93 + if err != nil {
94 + t.Fatalf("Server failed to decrypt: %v", err)
95 + }
96 +
97 + if !bytes.Equal(decrypted, testMessage) {
98 + t.Errorf("Decrypted message %q doesn't match original %q", decrypted, testMessage)
99 + }
100 +
101 + // Server encrypts response
102 + serverEncryptNonce := make([]byte, nonceSize)
103 + copy(serverEncryptNonce, serverNonce) // Start with server nonce
104 + responseMessage := []byte("Hello back!")
105 + encryptedResponse := serverAEAD.Seal(nil, serverEncryptNonce, responseMessage, nil)
106 +
107 + // Client decrypts response
108 + clientDecryptNonce := make([]byte, nonceSize)
109 + copy(clientDecryptNonce, serverNonce) // Use same nonce as server
110 + decryptedResponse, err := clientAEAD.Open(nil, clientDecryptNonce, encryptedResponse, nil)
111 + if err != nil {
112 + t.Fatalf("Client failed to decrypt response: %v", err)
113 + }
114 +
115 + if !bytes.Equal(decryptedResponse, responseMessage) {
116 + t.Errorf("Decrypted response %q doesn't match original %q", decryptedResponse, responseMessage)
117 + }
118 +}
relaydns/core/cryptoops/packet_size_test.go new
+84
@@ -0,0 +1,84 @@
1 +package cryptoops
2 +
3 +import (
4 + "bytes"
5 + "io"
6 + "testing"
7 +)
8 +
9 +// TestPacketSizeLimit tests that packets larger than the limit are rejected
10 +func TestPacketSizeLimit(t *testing.T) {
11 + // Create a mock connection that sends a packet larger than maxRawPacketSize
12 + largePacketSize := maxRawPacketSize + 1
13 +
14 + // Create a buffer with length prefix indicating a large packet
15 + buf := make([]byte, 4+largePacketSize)
16 +
17 + // Write big-endian length
18 + buf[0] = byte(largePacketSize >> 24)
19 + buf[1] = byte(largePacketSize >> 16)
20 + buf[2] = byte(largePacketSize >> 8)
21 + buf[3] = byte(largePacketSize)
22 +
23 + // Fill the rest with dummy data
24 + for i := 4; i < len(buf); i++ {
25 + buf[i] = 0x42
26 + }
27 +
28 + // Create a reader that returns our large packet
29 + reader := bytes.NewReader(buf)
30 +
31 + // Try to read the length-prefixed message
32 + _, err := readLengthPrefixed(reader)
33 +
34 + // Should fail with ErrHandshakeFailed
35 + if err != ErrHandshakeFailed {
36 + t.Errorf("Expected ErrHandshakeFailed for oversized packet, got: %v", err)
37 + }
38 +}
39 +
40 +// TestSecureConnectionPacketSizeLimit tests that SecureConnection rejects oversized packets
41 +func TestSecureConnectionPacketSizeLimit(t *testing.T) {
42 + // Create a mock connection that sends a packet larger than maxRawPacketSize
43 + largePacketSize := maxRawPacketSize + 1
44 +
45 + // Create a buffer with length prefix indicating a large packet
46 + buf := make([]byte, 4+largePacketSize)
47 +
48 + // Write big-endian length
49 + buf[0] = byte(largePacketSize >> 24)
50 + buf[1] = byte(largePacketSize >> 16)
51 + buf[2] = byte(largePacketSize >> 8)
52 + buf[3] = byte(largePacketSize)
53 +
54 + // Fill the rest with dummy data
55 + for i := 4; i < len(buf); i++ {
56 + buf[i] = 0x42
57 + }
58 +
59 + // Create a pipe connection
60 + reader, writer := io.Pipe()
61 +
62 + // Write the large packet to the writer in a goroutine
63 + go func() {
64 + writer.Write(buf)
65 + writer.Close()
66 + }()
67 +
68 + // Create a mock secure connection using pipeConn
69 + sc := &SecureConnection{
70 + conn: &pipeConn{
71 + reader: reader,
72 + writer: writer,
73 + },
74 + }
75 +
76 + // Try to read from the secure connection
77 + readBuf := make([]byte, 1024)
78 + _, err := sc.Read(readBuf)
79 +
80 + // Should fail with ErrDecryptionFailed
81 + if err != ErrDecryptionFailed {
82 + t.Errorf("Expected ErrDecryptionFailed for oversized packet in SecureConnection, got: %v", err)
83 + }
84 +}
relaydns/core/cryptoops/sig.go new
+69
@@ -0,0 +1,69 @@
1 +package cryptoops
2 +
3 +import (
4 + "crypto/ed25519"
5 + "crypto/hmac"
6 + "crypto/rand"
7 + "crypto/sha256"
8 + "encoding/base32"
9 + "errors"
10 +)
11 +
12 +var _id_magic = []byte("RDVERB_PROTOCOL_VER_01_SHA256_ID")
13 +
14 +func DeriveID(publickey ed25519.PublicKey) string {
15 + h := hmac.New(sha256.New, _id_magic)
16 + h.Write(publickey)
17 + return base32.StdEncoding.EncodeToString(h.Sum(nil))
18 +}
19 +
20 +type Credential struct {
21 + privateKey ed25519.PrivateKey
22 + publicKey ed25519.PublicKey
23 + id string
24 +}
25 +
26 +func NewCredentialFromPrivateKey(privateKey ed25519.PrivateKey) (*Credential, error) {
27 + if len(privateKey) != ed25519.PrivateKeySize {
28 + return nil, errors.New("invalid private key length")
29 + }
30 +
31 + publicKey := privateKey.Public().(ed25519.PublicKey)
32 + return &Credential{
33 + privateKey: privateKey,
34 + publicKey: publicKey,
35 + id: DeriveID(publicKey),
36 + }, nil
37 +}
38 +
39 +func NewCredential() (*Credential, error) {
40 + _, privateKey, err := ed25519.GenerateKey(rand.Reader)
41 + if err != nil {
42 + return nil, err
43 + }
44 +
45 + return NewCredentialFromPrivateKey(privateKey)
46 +}
47 +
48 +func (c *Credential) ID() string {
49 + return c.id
50 +}
51 +
52 +func (c *Credential) Sign(data []byte) []byte {
53 + return ed25519.Sign(c.privateKey, data)
54 +}
55 +
56 +func (c *Credential) Verify(data, sig []byte) bool {
57 + if len(sig) != ed25519.SignatureSize {
58 + return false
59 + }
60 + return ed25519.Verify(c.publicKey, data, sig)
61 +}
62 +
63 +func (c *Credential) PublicKey() ed25519.PublicKey {
64 + return c.publicKey
65 +}
66 +
67 +func (c *Credential) PrivateKey() ed25519.PrivateKey {
68 + return c.privateKey
69 +}
relaydns/core/cryptoops/simple_test.go new
+195
@@ -0,0 +1,195 @@
1 +package cryptoops
2 +
3 +import (
4 + "bytes"
5 + "io"
6 + "testing"
7 + "time"
8 +)
9 +
10 +// TestPipeConnection tests the basic pipe connection functionality
11 +func TestPipeConnection(t *testing.T) {
12 + // Create a pipe for bidirectional communication
13 + reader, writer := io.Pipe()
14 +
15 + // Test writing and reading
16 + testData := []byte("Hello, world!")
17 +
18 + // Write data in a goroutine
19 + go func() {
20 + writer.Write(testData)
21 + writer.Close()
22 + }()
23 +
24 + // Read data
25 + receivedData := make([]byte, 1024)
26 + n, err := reader.Read(receivedData)
27 + if err != nil {
28 + t.Fatalf("Failed to read from pipe: %v", err)
29 + }
30 +
31 + received := receivedData[:n]
32 + if !bytes.Equal(received, testData) {
33 + t.Fatalf("Received %q, expected %q", received, testData)
34 + }
35 +}
36 +
37 +// TestLengthPrefixedWriteRead tests the length-prefixed write/read functions
38 +func TestLengthPrefixedWriteRead(t *testing.T) {
39 + // Create a pipe for bidirectional communication
40 + reader, writer := io.Pipe()
41 +
42 + testData := []byte("Hello, world!")
43 +
44 + // Write length-prefixed data in a goroutine
45 + go func() {
46 + err := writeLengthPrefixed(writer, testData)
47 + if err != nil {
48 + t.Errorf("Failed to write length-prefixed data: %v", err)
49 + }
50 + writer.Close()
51 + }()
52 +
53 + // Read length-prefixed data
54 + receivedData, err := readLengthPrefixed(reader)
55 + if err != nil {
56 + t.Fatalf("Failed to read length-prefixed data: %v", err)
57 + }
58 +
59 + if !bytes.Equal(receivedData, testData) {
60 + t.Fatalf("Received %q, expected %q", receivedData, testData)
61 + }
62 +}
63 +
64 +// TestPipeConn tests the pipe connection wrapper
65 +func TestPipeConn(t *testing.T) {
66 + // Create a pipe for bidirectional communication
67 + reader, writer := io.Pipe()
68 +
69 + // Create pipe connection
70 + conn := &pipeConn{
71 + reader: reader,
72 + writer: writer,
73 + }
74 +
75 + testData := []byte("Hello, world!")
76 +
77 + // Write data in a goroutine
78 + go func() {
79 + n, err := conn.Write(testData)
80 + if err != nil {
81 + t.Errorf("Failed to write to pipe connection: %v", err)
82 + }
83 + if n != len(testData) {
84 + t.Errorf("Wrote %d bytes, expected %d", n, len(testData))
85 + }
86 + conn.Close()
87 + }()
88 +
89 + // Read data
90 + receivedData := make([]byte, 1024)
91 + n, err := conn.Read(receivedData)
92 + if err != nil {
93 + t.Fatalf("Failed to read from pipe connection: %v", err)
94 + }
95 +
96 + received := receivedData[:n]
97 + if !bytes.Equal(received, testData) {
98 + t.Fatalf("Received %q, expected %q", received, testData)
99 + }
100 +}
101 +
102 +// TestBidirectionalPipeConn tests bidirectional communication with pipe connections
103 +func TestBidirectionalPipeConn(t *testing.T) {
104 + // Create pipes for bidirectional communication
105 + clientReader, clientWriter := io.Pipe()
106 + serverReader, serverWriter := io.Pipe()
107 +
108 + // Create pipe connections
109 + clientConn := &pipeConn{
110 + reader: clientReader,
111 + writer: serverWriter,
112 + }
113 + serverConn := &pipeConn{
114 + reader: serverReader,
115 + writer: clientWriter,
116 + }
117 +
118 + clientData := []byte("Hello from client!")
119 + serverData := []byte("Hello from server!")
120 +
121 + // Use channels to coordinate
122 + done := make(chan bool, 2)
123 +
124 + // Client writes data and reads response
125 + go func() {
126 + defer func() { done <- true }()
127 +
128 + // Client writes data
129 + n, err := clientConn.Write(clientData)
130 + if err != nil {
131 + t.Errorf("Failed to write from client: %v", err)
132 + return
133 + }
134 + if n != len(clientData) {
135 + t.Errorf("Client wrote %d bytes, expected %d", n, len(clientData))
136 + return
137 + }
138 +
139 + // Client reads response
140 + clientReadBuf := make([]byte, 1024)
141 + n, err = clientConn.Read(clientReadBuf)
142 + if err != nil {
143 + t.Errorf("Failed to read at client: %v", err)
144 + return
145 + }
146 +
147 + receivedServerData := clientReadBuf[:n]
148 + if !bytes.Equal(receivedServerData, serverData) {
149 + t.Errorf("Client received %q, expected %q", receivedServerData, serverData)
150 + }
151 + }()
152 +
153 + // Server reads data and writes response
154 + go func() {
155 + defer func() { done <- true }()
156 +
157 + // Server reads data
158 + serverReadBuf := make([]byte, 1024)
159 + n, err := serverConn.Read(serverReadBuf)
160 + if err != nil {
161 + t.Errorf("Failed to read at server: %v", err)
162 + return
163 + }
164 +
165 + receivedClientData := serverReadBuf[:n]
166 + if !bytes.Equal(receivedClientData, clientData) {
167 + t.Errorf("Server received %q, expected %q", receivedClientData, clientData)
168 + return
169 + }
170 +
171 + // Server writes response
172 + n, err = serverConn.Write(serverData)
173 + if err != nil {
174 + t.Errorf("Failed to write from server: %v", err)
175 + return
176 + }
177 + if n != len(serverData) {
178 + t.Errorf("Server wrote %d bytes, expected %d", n, len(serverData))
179 + }
180 + }()
181 +
182 + // Wait for both goroutines to complete
183 + for i := 0; i < 2; i++ {
184 + select {
185 + case <-done:
186 + // One goroutine completed
187 + case <-time.After(5 * time.Second):
188 + t.Fatal("Test timed out")
189 + }
190 + }
191 +
192 + // Close connections
193 + clientConn.Close()
194 + serverConn.Close()
195 +}
relaydns/core/proto/rdsec/rdsec.pb.go new
+482
@@ -0,0 +1,482 @@
1 +// Code generated by protoc-gen-go. DO NOT EDIT.
2 +// versions:
3 +// protoc-gen-go v1.36.10
4 +// protoc (unknown)
5 +// source: relaydns/core/proto/rdsec/rdsec.proto
6 +
7 +package rdsec
8 +
9 +import (
10 + protoreflect "google.golang.org/protobuf/reflect/protoreflect"
11 + protoimpl "google.golang.org/protobuf/runtime/protoimpl"
12 + reflect "reflect"
13 + sync "sync"
14 + unsafe "unsafe"
15 +)
16 +
17 +const (
18 + // Verify that this generated code is sufficiently up-to-date.
19 + _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
20 + // Verify that runtime/protoimpl is sufficiently up-to-date.
21 + _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
22 +)
23 +
24 +type ProtocolVersion int32
25 +
26 +const (
27 + ProtocolVersion_PROTOCOL_VERSION_1 ProtocolVersion = 0
28 +)
29 +
30 +// Enum value maps for ProtocolVersion.
31 +var (
32 + ProtocolVersion_name = map[int32]string{
33 + 0: "PROTOCOL_VERSION_1",
34 + }
35 + ProtocolVersion_value = map[string]int32{
36 + "PROTOCOL_VERSION_1": 0,
37 + }
38 +)
39 +
40 +func (x ProtocolVersion) Enum() *ProtocolVersion {
41 + p := new(ProtocolVersion)
42 + *p = x
43 + return p
44 +}
45 +
46 +func (x ProtocolVersion) String() string {
47 + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
48 +}
49 +
50 +func (ProtocolVersion) Descriptor() protoreflect.EnumDescriptor {
51 + return file_relaydns_core_proto_rdsec_rdsec_proto_enumTypes[0].Descriptor()
52 +}
53 +
54 +func (ProtocolVersion) Type() protoreflect.EnumType {
55 + return &file_relaydns_core_proto_rdsec_rdsec_proto_enumTypes[0]
56 +}
57 +
58 +func (x ProtocolVersion) Number() protoreflect.EnumNumber {
59 + return protoreflect.EnumNumber(x)
60 +}
61 +
62 +// Deprecated: Use ProtocolVersion.Descriptor instead.
63 +func (ProtocolVersion) EnumDescriptor() ([]byte, []int) {
64 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{0}
65 +}
66 +
67 +type Identity struct {
68 + state protoimpl.MessageState `protogen:"open.v1"`
69 + Id string `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"`
70 + PublicKey []byte `protobuf:"bytes,2,opt,name=public_key,json=publicKey,proto3" json:"public_key,omitempty"`
71 + unknownFields protoimpl.UnknownFields
72 + sizeCache protoimpl.SizeCache
73 +}
74 +
75 +func (x *Identity) Reset() {
76 + *x = Identity{}
77 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[0]
78 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
79 + ms.StoreMessageInfo(mi)
80 +}
81 +
82 +func (x *Identity) String() string {
83 + return protoimpl.X.MessageStringOf(x)
84 +}
85 +
86 +func (*Identity) ProtoMessage() {}
87 +
88 +func (x *Identity) ProtoReflect() protoreflect.Message {
89 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[0]
90 + if x != nil {
91 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
92 + if ms.LoadMessageInfo() == nil {
93 + ms.StoreMessageInfo(mi)
94 + }
95 + return ms
96 + }
97 + return mi.MessageOf(x)
98 +}
99 +
100 +// Deprecated: Use Identity.ProtoReflect.Descriptor instead.
101 +func (*Identity) Descriptor() ([]byte, []int) {
102 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{0}
103 +}
104 +
105 +func (x *Identity) GetId() string {
106 + if x != nil {
107 + return x.Id
108 + }
109 + return ""
110 +}
111 +
112 +func (x *Identity) GetPublicKey() []byte {
113 + if x != nil {
114 + return x.PublicKey
115 + }
116 + return nil
117 +}
118 +
119 +type ClientInitPayload struct {
120 + state protoimpl.MessageState `protogen:"open.v1"`
121 + Version ProtocolVersion `protobuf:"varint,1,opt,name=version,proto3,enum=rdsec.ProtocolVersion" json:"version,omitempty"`
122 + Nonce []byte `protobuf:"bytes,2,opt,name=nonce,proto3" json:"nonce,omitempty"`
123 + Timestamp int64 `protobuf:"varint,3,opt,name=timestamp,proto3" json:"timestamp,omitempty"`
124 + Identity *Identity `protobuf:"bytes,4,opt,name=identity,proto3" json:"identity,omitempty"`
125 + Alpn string `protobuf:"bytes,5,opt,name=alpn,proto3" json:"alpn,omitempty"`
126 + SessionPublicKey []byte `protobuf:"bytes,6,opt,name=session_public_key,json=sessionPublicKey,proto3" json:"session_public_key,omitempty"`
127 + unknownFields protoimpl.UnknownFields
128 + sizeCache protoimpl.SizeCache
129 +}
130 +
131 +func (x *ClientInitPayload) Reset() {
132 + *x = ClientInitPayload{}
133 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[1]
134 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
135 + ms.StoreMessageInfo(mi)
136 +}
137 +
138 +func (x *ClientInitPayload) String() string {
139 + return protoimpl.X.MessageStringOf(x)
140 +}
141 +
142 +func (*ClientInitPayload) ProtoMessage() {}
143 +
144 +func (x *ClientInitPayload) ProtoReflect() protoreflect.Message {
145 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[1]
146 + if x != nil {
147 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
148 + if ms.LoadMessageInfo() == nil {
149 + ms.StoreMessageInfo(mi)
150 + }
151 + return ms
152 + }
153 + return mi.MessageOf(x)
154 +}
155 +
156 +// Deprecated: Use ClientInitPayload.ProtoReflect.Descriptor instead.
157 +func (*ClientInitPayload) Descriptor() ([]byte, []int) {
158 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{1}
159 +}
160 +
161 +func (x *ClientInitPayload) GetVersion() ProtocolVersion {
162 + if x != nil {
163 + return x.Version
164 + }
165 + return ProtocolVersion_PROTOCOL_VERSION_1
166 +}
167 +
168 +func (x *ClientInitPayload) GetNonce() []byte {
169 + if x != nil {
170 + return x.Nonce
171 + }
172 + return nil
173 +}
174 +
175 +func (x *ClientInitPayload) GetTimestamp() int64 {
176 + if x != nil {
177 + return x.Timestamp
178 + }
179 + return 0
180 +}
181 +
182 +func (x *ClientInitPayload) GetIdentity() *Identity {
183 + if x != nil {
184 + return x.Identity
185 + }
186 + return nil
187 +}
188 +
189 +func (x *ClientInitPayload) GetAlpn() string {
190 + if x != nil {
191 + return x.Alpn
192 + }
193 + return ""
194 +}
195 +
196 +func (x *ClientInitPayload) GetSessionPublicKey() []byte {
197 + if x != nil {
198 + return x.SessionPublicKey
199 + }
200 + return nil
201 +}
202 +
203 +type SignedPayload struct {
204 + state protoimpl.MessageState `protogen:"open.v1"`
205 + Data []byte `protobuf:"bytes,1,opt,name=data,proto3" json:"data,omitempty"`
206 + Signature []byte `protobuf:"bytes,2,opt,name=signature,proto3" json:"signature,omitempty"`
207 + unknownFields protoimpl.UnknownFields
208 + sizeCache protoimpl.SizeCache
209 +}
210 +
211 +func (x *SignedPayload) Reset() {
212 + *x = SignedPayload{}
213 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[2]
214 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
215 + ms.StoreMessageInfo(mi)
216 +}
217 +
218 +func (x *SignedPayload) String() string {
219 + return protoimpl.X.MessageStringOf(x)
220 +}
221 +
222 +func (*SignedPayload) ProtoMessage() {}
223 +
224 +func (x *SignedPayload) ProtoReflect() protoreflect.Message {
225 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[2]
226 + if x != nil {
227 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
228 + if ms.LoadMessageInfo() == nil {
229 + ms.StoreMessageInfo(mi)
230 + }
231 + return ms
232 + }
233 + return mi.MessageOf(x)
234 +}
235 +
236 +// Deprecated: Use SignedPayload.ProtoReflect.Descriptor instead.
237 +func (*SignedPayload) Descriptor() ([]byte, []int) {
238 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{2}
239 +}
240 +
241 +func (x *SignedPayload) GetData() []byte {
242 + if x != nil {
243 + return x.Data
244 + }
245 + return nil
246 +}
247 +
248 +func (x *SignedPayload) GetSignature() []byte {
249 + if x != nil {
250 + return x.Signature
251 + }
252 + return nil
253 +}
254 +
255 +type ServerInitPayload struct {
256 + state protoimpl.MessageState `protogen:"open.v1"`
257 + Version ProtocolVersion `protobuf:"varint,1,opt,name=version,proto3,enum=rdsec.ProtocolVersion" json:"version,omitempty"`
258 + Nonce []byte `protobuf:"bytes,2,opt,name=nonce,proto3" json:"nonce,omitempty"`
259 + Timestamp int64 `protobuf:"varint,3,opt,name=timestamp,proto3" json:"timestamp,omitempty"`
260 + Identity *Identity `protobuf:"bytes,4,opt,name=identity,proto3" json:"identity,omitempty"`
261 + Alpn string `protobuf:"bytes,5,opt,name=alpn,proto3" json:"alpn,omitempty"`
262 + SessionPublicKey []byte `protobuf:"bytes,6,opt,name=session_public_key,json=sessionPublicKey,proto3" json:"session_public_key,omitempty"`
263 + unknownFields protoimpl.UnknownFields
264 + sizeCache protoimpl.SizeCache
265 +}
266 +
267 +func (x *ServerInitPayload) Reset() {
268 + *x = ServerInitPayload{}
269 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[3]
270 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
271 + ms.StoreMessageInfo(mi)
272 +}
273 +
274 +func (x *ServerInitPayload) String() string {
275 + return protoimpl.X.MessageStringOf(x)
276 +}
277 +
278 +func (*ServerInitPayload) ProtoMessage() {}
279 +
280 +func (x *ServerInitPayload) ProtoReflect() protoreflect.Message {
281 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[3]
282 + if x != nil {
283 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
284 + if ms.LoadMessageInfo() == nil {
285 + ms.StoreMessageInfo(mi)
286 + }
287 + return ms
288 + }
289 + return mi.MessageOf(x)
290 +}
291 +
292 +// Deprecated: Use ServerInitPayload.ProtoReflect.Descriptor instead.
293 +func (*ServerInitPayload) Descriptor() ([]byte, []int) {
294 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{3}
295 +}
296 +
297 +func (x *ServerInitPayload) GetVersion() ProtocolVersion {
298 + if x != nil {
299 + return x.Version
300 + }
301 + return ProtocolVersion_PROTOCOL_VERSION_1
302 +}
303 +
304 +func (x *ServerInitPayload) GetNonce() []byte {
305 + if x != nil {
306 + return x.Nonce
307 + }
308 + return nil
309 +}
310 +
311 +func (x *ServerInitPayload) GetTimestamp() int64 {
312 + if x != nil {
313 + return x.Timestamp
314 + }
315 + return 0
316 +}
317 +
318 +func (x *ServerInitPayload) GetIdentity() *Identity {
319 + if x != nil {
320 + return x.Identity
321 + }
322 + return nil
323 +}
324 +
325 +func (x *ServerInitPayload) GetAlpn() string {
326 + if x != nil {
327 + return x.Alpn
328 + }
329 + return ""
330 +}
331 +
332 +func (x *ServerInitPayload) GetSessionPublicKey() []byte {
333 + if x != nil {
334 + return x.SessionPublicKey
335 + }
336 + return nil
337 +}
338 +
339 +type EncryptedData struct {
340 + state protoimpl.MessageState `protogen:"open.v1"`
341 + Nonce []byte `protobuf:"bytes,1,opt,name=nonce,proto3" json:"nonce,omitempty"`
342 + Payload []byte `protobuf:"bytes,2,opt,name=payload,proto3" json:"payload,omitempty"`
343 + unknownFields protoimpl.UnknownFields
344 + sizeCache protoimpl.SizeCache
345 +}
346 +
347 +func (x *EncryptedData) Reset() {
348 + *x = EncryptedData{}
349 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[4]
350 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
351 + ms.StoreMessageInfo(mi)
352 +}
353 +
354 +func (x *EncryptedData) String() string {
355 + return protoimpl.X.MessageStringOf(x)
356 +}
357 +
358 +func (*EncryptedData) ProtoMessage() {}
359 +
360 +func (x *EncryptedData) ProtoReflect() protoreflect.Message {
361 + mi := &file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes[4]
362 + if x != nil {
363 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
364 + if ms.LoadMessageInfo() == nil {
365 + ms.StoreMessageInfo(mi)
366 + }
367 + return ms
368 + }
369 + return mi.MessageOf(x)
370 +}
371 +
372 +// Deprecated: Use EncryptedData.ProtoReflect.Descriptor instead.
373 +func (*EncryptedData) Descriptor() ([]byte, []int) {
374 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP(), []int{4}
375 +}
376 +
377 +func (x *EncryptedData) GetNonce() []byte {
378 + if x != nil {
379 + return x.Nonce
380 + }
381 + return nil
382 +}
383 +
384 +func (x *EncryptedData) GetPayload() []byte {
385 + if x != nil {
386 + return x.Payload
387 + }
388 + return nil
389 +}
390 +
391 +var File_relaydns_core_proto_rdsec_rdsec_proto protoreflect.FileDescriptor
392 +
393 +const file_relaydns_core_proto_rdsec_rdsec_proto_rawDesc = "" +
394 + "\n" +
395 + "%relaydns/core/proto/rdsec/rdsec.proto\x12\x05rdsec\"9\n" +
396 + "\bIdentity\x12\x0e\n" +
397 + "\x02id\x18\x01 \x01(\tR\x02id\x12\x1d\n" +
398 + "\n" +
399 + "public_key\x18\x02 \x01(\fR\tpublicKey\"\xe8\x01\n" +
400 + "\x11ClientInitPayload\x120\n" +
401 + "\aversion\x18\x01 \x01(\x0e2\x16.rdsec.ProtocolVersionR\aversion\x12\x14\n" +
402 + "\x05nonce\x18\x02 \x01(\fR\x05nonce\x12\x1c\n" +
403 + "\ttimestamp\x18\x03 \x01(\x03R\ttimestamp\x12+\n" +
404 + "\bidentity\x18\x04 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x12\n" +
405 + "\x04alpn\x18\x05 \x01(\tR\x04alpn\x12,\n" +
406 + "\x12session_public_key\x18\x06 \x01(\fR\x10sessionPublicKey\"A\n" +
407 + "\rSignedPayload\x12\x12\n" +
408 + "\x04data\x18\x01 \x01(\fR\x04data\x12\x1c\n" +
409 + "\tsignature\x18\x02 \x01(\fR\tsignature\"\xe8\x01\n" +
410 + "\x11ServerInitPayload\x120\n" +
411 + "\aversion\x18\x01 \x01(\x0e2\x16.rdsec.ProtocolVersionR\aversion\x12\x14\n" +
412 + "\x05nonce\x18\x02 \x01(\fR\x05nonce\x12\x1c\n" +
413 + "\ttimestamp\x18\x03 \x01(\x03R\ttimestamp\x12+\n" +
414 + "\bidentity\x18\x04 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x12\n" +
415 + "\x04alpn\x18\x05 \x01(\tR\x04alpn\x12,\n" +
416 + "\x12session_public_key\x18\x06 \x01(\fR\x10sessionPublicKey\"?\n" +
417 + "\rEncryptedData\x12\x14\n" +
418 + "\x05nonce\x18\x01 \x01(\fR\x05nonce\x12\x18\n" +
419 + "\apayload\x18\x02 \x01(\fR\apayload*)\n" +
420 + "\x0fProtocolVersion\x12\x16\n" +
421 + "\x12PROTOCOL_VERSION_1\x10\x00B\x87\x01\n" +
422 + "\tcom.rdsecB\n" +
423 + "RdsecProtoP\x01Z:github.com/gosuda/relaydns/relaydns/core/proto/rdsec;rdsec\xa2\x02\x03RXX\xaa\x02\x05Rdsec\xca\x02\x05Rdsec\xe2\x02\x11Rdsec\\GPBMetadata\xea\x02\x05Rdsecb\x06proto3"
424 +
425 +var (
426 + file_relaydns_core_proto_rdsec_rdsec_proto_rawDescOnce sync.Once
427 + file_relaydns_core_proto_rdsec_rdsec_proto_rawDescData []byte
428 +)
429 +
430 +func file_relaydns_core_proto_rdsec_rdsec_proto_rawDescGZIP() []byte {
431 + file_relaydns_core_proto_rdsec_rdsec_proto_rawDescOnce.Do(func() {
432 + file_relaydns_core_proto_rdsec_rdsec_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_relaydns_core_proto_rdsec_rdsec_proto_rawDesc), len(file_relaydns_core_proto_rdsec_rdsec_proto_rawDesc)))
433 + })
434 + return file_relaydns_core_proto_rdsec_rdsec_proto_rawDescData
435 +}
436 +
437 +var file_relaydns_core_proto_rdsec_rdsec_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
438 +var file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes = make([]protoimpl.MessageInfo, 5)
439 +var file_relaydns_core_proto_rdsec_rdsec_proto_goTypes = []any{
440 + (ProtocolVersion)(0), // 0: rdsec.ProtocolVersion
441 + (*Identity)(nil), // 1: rdsec.Identity
442 + (*ClientInitPayload)(nil), // 2: rdsec.ClientInitPayload
443 + (*SignedPayload)(nil), // 3: rdsec.SignedPayload
444 + (*ServerInitPayload)(nil), // 4: rdsec.ServerInitPayload
445 + (*EncryptedData)(nil), // 5: rdsec.EncryptedData
446 +}
447 +var file_relaydns_core_proto_rdsec_rdsec_proto_depIdxs = []int32{
448 + 0, // 0: rdsec.ClientInitPayload.version:type_name -> rdsec.ProtocolVersion
449 + 1, // 1: rdsec.ClientInitPayload.identity:type_name -> rdsec.Identity
450 + 0, // 2: rdsec.ServerInitPayload.version:type_name -> rdsec.ProtocolVersion
451 + 1, // 3: rdsec.ServerInitPayload.identity:type_name -> rdsec.Identity
452 + 4, // [4:4] is the sub-list for method output_type
453 + 4, // [4:4] is the sub-list for method input_type
454 + 4, // [4:4] is the sub-list for extension type_name
455 + 4, // [4:4] is the sub-list for extension extendee
456 + 0, // [0:4] is the sub-list for field type_name
457 +}
458 +
459 +func init() { file_relaydns_core_proto_rdsec_rdsec_proto_init() }
460 +func file_relaydns_core_proto_rdsec_rdsec_proto_init() {
461 + if File_relaydns_core_proto_rdsec_rdsec_proto != nil {
462 + return
463 + }
464 + type x struct{}
465 + out := protoimpl.TypeBuilder{
466 + File: protoimpl.DescBuilder{
467 + GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
468 + RawDescriptor: unsafe.Slice(unsafe.StringData(file_relaydns_core_proto_rdsec_rdsec_proto_rawDesc), len(file_relaydns_core_proto_rdsec_rdsec_proto_rawDesc)),
469 + NumEnums: 1,
470 + NumMessages: 5,
471 + NumExtensions: 0,
472 + NumServices: 0,
473 + },
474 + GoTypes: file_relaydns_core_proto_rdsec_rdsec_proto_goTypes,
475 + DependencyIndexes: file_relaydns_core_proto_rdsec_rdsec_proto_depIdxs,
476 + EnumInfos: file_relaydns_core_proto_rdsec_rdsec_proto_enumTypes,
477 + MessageInfos: file_relaydns_core_proto_rdsec_rdsec_proto_msgTypes,
478 + }.Build()
479 + File_relaydns_core_proto_rdsec_rdsec_proto = out.File
480 + file_relaydns_core_proto_rdsec_rdsec_proto_goTypes = nil
481 + file_relaydns_core_proto_rdsec_rdsec_proto_depIdxs = nil
482 +}
relaydns/core/proto/rdsec/rdsec.proto new
+44
@@ -0,0 +1,44 @@
1 +syntax = "proto3";
2 +
3 +package rdsec;
4 +
5 +option go_package = "github.com/gosuda/relaydns/relaydns/core/proto/rdsec;rdsec";
6 +
7 +message Identity {
8 + string id = 1;
9 + bytes public_key = 2;
10 +}
11 +
12 +enum ProtocolVersion {
13 + PROTOCOL_VERSION_1 = 0;
14 +}
15 +
16 +message ClientInitPayload {
17 + ProtocolVersion version = 1;
18 + bytes nonce = 2;
19 + int64 timestamp = 3;
20 + Identity identity = 4;
21 + string alpn = 5;
22 +
23 + bytes session_public_key = 6;
24 +}
25 +
26 +message SignedPayload {
27 + bytes data = 1;
28 + bytes signature = 2;
29 +}
30 +
31 +message ServerInitPayload {
32 + ProtocolVersion version = 1;
33 + bytes nonce = 2;
34 + int64 timestamp = 3;
35 + Identity identity = 4;
36 + string alpn = 5;
37 +
38 + bytes session_public_key = 6;
39 +}
40 +
41 +message EncryptedData {
42 + bytes nonce = 1;
43 + bytes payload = 2;
44 +}
relaydns/core/proto/rdsec/rdsec_vtproto.pb.go new
+2581
@@ -0,0 +1,2581 @@
1 +// Code generated by protoc-gen-go-vtproto. DO NOT EDIT.
2 +// protoc-gen-go-vtproto version: v0.6.0
3 +// source: relaydns/core/proto/rdsec/rdsec.proto
4 +
5 +package rdsec
6 +
7 +import (
8 + fmt "fmt"
9 + protohelpers "github.com/planetscale/vtprotobuf/protohelpers"
10 + proto "google.golang.org/protobuf/proto"
11 + protoimpl "google.golang.org/protobuf/runtime/protoimpl"
12 + io "io"
13 + unsafe "unsafe"
14 +)
15 +
16 +const (
17 + // Verify that this generated code is sufficiently up-to-date.
18 + _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
19 + // Verify that runtime/protoimpl is sufficiently up-to-date.
20 + _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
21 +)
22 +
23 +func (m *Identity) CloneVT() *Identity {
24 + if m == nil {
25 + return (*Identity)(nil)
26 + }
27 + r := new(Identity)
28 + r.Id = m.Id
29 + if rhs := m.PublicKey; rhs != nil {
30 + tmpBytes := make([]byte, len(rhs))
31 + copy(tmpBytes, rhs)
32 + r.PublicKey = tmpBytes
33 + }
34 + if len(m.unknownFields) > 0 {
35 + r.unknownFields = make([]byte, len(m.unknownFields))
36 + copy(r.unknownFields, m.unknownFields)
37 + }
38 + return r
39 +}
40 +
41 +func (m *Identity) CloneMessageVT() proto.Message {
42 + return m.CloneVT()
43 +}
44 +
45 +func (m *ClientInitPayload) CloneVT() *ClientInitPayload {
46 + if m == nil {
47 + return (*ClientInitPayload)(nil)
48 + }
49 + r := new(ClientInitPayload)
50 + r.Version = m.Version
51 + r.Timestamp = m.Timestamp
52 + r.Identity = m.Identity.CloneVT()
53 + r.Alpn = m.Alpn
54 + if rhs := m.Nonce; rhs != nil {
55 + tmpBytes := make([]byte, len(rhs))
56 + copy(tmpBytes, rhs)
57 + r.Nonce = tmpBytes
58 + }
59 + if rhs := m.SessionPublicKey; rhs != nil {
60 + tmpBytes := make([]byte, len(rhs))
61 + copy(tmpBytes, rhs)
62 + r.SessionPublicKey = tmpBytes
63 + }
64 + if len(m.unknownFields) > 0 {
65 + r.unknownFields = make([]byte, len(m.unknownFields))
66 + copy(r.unknownFields, m.unknownFields)
67 + }
68 + return r
69 +}
70 +
71 +func (m *ClientInitPayload) CloneMessageVT() proto.Message {
72 + return m.CloneVT()
73 +}
74 +
75 +func (m *SignedPayload) CloneVT() *SignedPayload {
76 + if m == nil {
77 + return (*SignedPayload)(nil)
78 + }
79 + r := new(SignedPayload)
80 + if rhs := m.Data; rhs != nil {
81 + tmpBytes := make([]byte, len(rhs))
82 + copy(tmpBytes, rhs)
83 + r.Data = tmpBytes
84 + }
85 + if rhs := m.Signature; rhs != nil {
86 + tmpBytes := make([]byte, len(rhs))
87 + copy(tmpBytes, rhs)
88 + r.Signature = tmpBytes
89 + }
90 + if len(m.unknownFields) > 0 {
91 + r.unknownFields = make([]byte, len(m.unknownFields))
92 + copy(r.unknownFields, m.unknownFields)
93 + }
94 + return r
95 +}
96 +
97 +func (m *SignedPayload) CloneMessageVT() proto.Message {
98 + return m.CloneVT()
99 +}
100 +
101 +func (m *ServerInitPayload) CloneVT() *ServerInitPayload {
102 + if m == nil {
103 + return (*ServerInitPayload)(nil)
104 + }
105 + r := new(ServerInitPayload)
106 + r.Version = m.Version
107 + r.Timestamp = m.Timestamp
108 + r.Identity = m.Identity.CloneVT()
109 + r.Alpn = m.Alpn
110 + if rhs := m.Nonce; rhs != nil {
111 + tmpBytes := make([]byte, len(rhs))
112 + copy(tmpBytes, rhs)
113 + r.Nonce = tmpBytes
114 + }
115 + if rhs := m.SessionPublicKey; rhs != nil {
116 + tmpBytes := make([]byte, len(rhs))
117 + copy(tmpBytes, rhs)
118 + r.SessionPublicKey = tmpBytes
119 + }
120 + if len(m.unknownFields) > 0 {
121 + r.unknownFields = make([]byte, len(m.unknownFields))
122 + copy(r.unknownFields, m.unknownFields)
123 + }
124 + return r
125 +}
126 +
127 +func (m *ServerInitPayload) CloneMessageVT() proto.Message {
128 + return m.CloneVT()
129 +}
130 +
131 +func (m *EncryptedData) CloneVT() *EncryptedData {
132 + if m == nil {
133 + return (*EncryptedData)(nil)
134 + }
135 + r := new(EncryptedData)
136 + if rhs := m.Nonce; rhs != nil {
137 + tmpBytes := make([]byte, len(rhs))
138 + copy(tmpBytes, rhs)
139 + r.Nonce = tmpBytes
140 + }
141 + if rhs := m.Payload; rhs != nil {
142 + tmpBytes := make([]byte, len(rhs))
143 + copy(tmpBytes, rhs)
144 + r.Payload = tmpBytes
145 + }
146 + if len(m.unknownFields) > 0 {
147 + r.unknownFields = make([]byte, len(m.unknownFields))
148 + copy(r.unknownFields, m.unknownFields)
149 + }
150 + return r
151 +}
152 +
153 +func (m *EncryptedData) CloneMessageVT() proto.Message {
154 + return m.CloneVT()
155 +}
156 +
157 +func (this *Identity) EqualVT(that *Identity) bool {
158 + if this == that {
159 + return true
160 + } else if this == nil || that == nil {
161 + return false
162 + }
163 + if this.Id != that.Id {
164 + return false
165 + }
166 + if string(this.PublicKey) != string(that.PublicKey) {
167 + return false
168 + }
169 + return string(this.unknownFields) == string(that.unknownFields)
170 +}
171 +
172 +func (this *Identity) EqualMessageVT(thatMsg proto.Message) bool {
173 + that, ok := thatMsg.(*Identity)
174 + if !ok {
175 + return false
176 + }
177 + return this.EqualVT(that)
178 +}
179 +func (this *ClientInitPayload) EqualVT(that *ClientInitPayload) bool {
180 + if this == that {
181 + return true
182 + } else if this == nil || that == nil {
183 + return false
184 + }
185 + if this.Version != that.Version {
186 + return false
187 + }
188 + if string(this.Nonce) != string(that.Nonce) {
189 + return false
190 + }
191 + if this.Timestamp != that.Timestamp {
192 + return false
193 + }
194 + if !this.Identity.EqualVT(that.Identity) {
195 + return false
196 + }
197 + if this.Alpn != that.Alpn {
198 + return false
199 + }
200 + if string(this.SessionPublicKey) != string(that.SessionPublicKey) {
201 + return false
202 + }
203 + return string(this.unknownFields) == string(that.unknownFields)
204 +}
205 +
206 +func (this *ClientInitPayload) EqualMessageVT(thatMsg proto.Message) bool {
207 + that, ok := thatMsg.(*ClientInitPayload)
208 + if !ok {
209 + return false
210 + }
211 + return this.EqualVT(that)
212 +}
213 +func (this *SignedPayload) EqualVT(that *SignedPayload) bool {
214 + if this == that {
215 + return true
216 + } else if this == nil || that == nil {
217 + return false
218 + }
219 + if string(this.Data) != string(that.Data) {
220 + return false
221 + }
222 + if string(this.Signature) != string(that.Signature) {
223 + return false
224 + }
225 + return string(this.unknownFields) == string(that.unknownFields)
226 +}
227 +
228 +func (this *SignedPayload) EqualMessageVT(thatMsg proto.Message) bool {
229 + that, ok := thatMsg.(*SignedPayload)
230 + if !ok {
231 + return false
232 + }
233 + return this.EqualVT(that)
234 +}
235 +func (this *ServerInitPayload) EqualVT(that *ServerInitPayload) bool {
236 + if this == that {
237 + return true
238 + } else if this == nil || that == nil {
239 + return false
240 + }
241 + if this.Version != that.Version {
242 + return false
243 + }
244 + if string(this.Nonce) != string(that.Nonce) {
245 + return false
246 + }
247 + if this.Timestamp != that.Timestamp {
248 + return false
249 + }
250 + if !this.Identity.EqualVT(that.Identity) {
251 + return false
252 + }
253 + if this.Alpn != that.Alpn {
254 + return false
255 + }
256 + if string(this.SessionPublicKey) != string(that.SessionPublicKey) {
257 + return false
258 + }
259 + return string(this.unknownFields) == string(that.unknownFields)
260 +}
261 +
262 +func (this *ServerInitPayload) EqualMessageVT(thatMsg proto.Message) bool {
263 + that, ok := thatMsg.(*ServerInitPayload)
264 + if !ok {
265 + return false
266 + }
267 + return this.EqualVT(that)
268 +}
269 +func (this *EncryptedData) EqualVT(that *EncryptedData) bool {
270 + if this == that {
271 + return true
272 + } else if this == nil || that == nil {
273 + return false
274 + }
275 + if string(this.Nonce) != string(that.Nonce) {
276 + return false
277 + }
278 + if string(this.Payload) != string(that.Payload) {
279 + return false
280 + }
281 + return string(this.unknownFields) == string(that.unknownFields)
282 +}
283 +
284 +func (this *EncryptedData) EqualMessageVT(thatMsg proto.Message) bool {
285 + that, ok := thatMsg.(*EncryptedData)
286 + if !ok {
287 + return false
288 + }
289 + return this.EqualVT(that)
290 +}
291 +func (m *Identity) MarshalVT() (dAtA []byte, err error) {
292 + if m == nil {
293 + return nil, nil
294 + }
295 + size := m.SizeVT()
296 + dAtA = make([]byte, size)
297 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
298 + if err != nil {
299 + return nil, err
300 + }
301 + return dAtA[:n], nil
302 +}
303 +
304 +func (m *Identity) MarshalToVT(dAtA []byte) (int, error) {
305 + size := m.SizeVT()
306 + return m.MarshalToSizedBufferVT(dAtA[:size])
307 +}
308 +
309 +func (m *Identity) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
310 + if m == nil {
311 + return 0, nil
312 + }
313 + i := len(dAtA)
314 + _ = i
315 + var l int
316 + _ = l
317 + if m.unknownFields != nil {
318 + i -= len(m.unknownFields)
319 + copy(dAtA[i:], m.unknownFields)
320 + }
321 + if len(m.PublicKey) > 0 {
322 + i -= len(m.PublicKey)
323 + copy(dAtA[i:], m.PublicKey)
324 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.PublicKey)))
325 + i--
326 + dAtA[i] = 0x12
327 + }
328 + if len(m.Id) > 0 {
329 + i -= len(m.Id)
330 + copy(dAtA[i:], m.Id)
331 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Id)))
332 + i--
333 + dAtA[i] = 0xa
334 + }
335 + return len(dAtA) - i, nil
336 +}
337 +
338 +func (m *ClientInitPayload) MarshalVT() (dAtA []byte, err error) {
339 + if m == nil {
340 + return nil, nil
341 + }
342 + size := m.SizeVT()
343 + dAtA = make([]byte, size)
344 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
345 + if err != nil {
346 + return nil, err
347 + }
348 + return dAtA[:n], nil
349 +}
350 +
351 +func (m *ClientInitPayload) MarshalToVT(dAtA []byte) (int, error) {
352 + size := m.SizeVT()
353 + return m.MarshalToSizedBufferVT(dAtA[:size])
354 +}
355 +
356 +func (m *ClientInitPayload) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
357 + if m == nil {
358 + return 0, nil
359 + }
360 + i := len(dAtA)
361 + _ = i
362 + var l int
363 + _ = l
364 + if m.unknownFields != nil {
365 + i -= len(m.unknownFields)
366 + copy(dAtA[i:], m.unknownFields)
367 + }
368 + if len(m.SessionPublicKey) > 0 {
369 + i -= len(m.SessionPublicKey)
370 + copy(dAtA[i:], m.SessionPublicKey)
371 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.SessionPublicKey)))
372 + i--
373 + dAtA[i] = 0x32
374 + }
375 + if len(m.Alpn) > 0 {
376 + i -= len(m.Alpn)
377 + copy(dAtA[i:], m.Alpn)
378 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn)))
379 + i--
380 + dAtA[i] = 0x2a
381 + }
382 + if m.Identity != nil {
383 + size, err := m.Identity.MarshalToSizedBufferVT(dAtA[:i])
384 + if err != nil {
385 + return 0, err
386 + }
387 + i -= size
388 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
389 + i--
390 + dAtA[i] = 0x22
391 + }
392 + if m.Timestamp != 0 {
393 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
394 + i--
395 + dAtA[i] = 0x18
396 + }
397 + if len(m.Nonce) > 0 {
398 + i -= len(m.Nonce)
399 + copy(dAtA[i:], m.Nonce)
400 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
401 + i--
402 + dAtA[i] = 0x12
403 + }
404 + if m.Version != 0 {
405 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Version))
406 + i--
407 + dAtA[i] = 0x8
408 + }
409 + return len(dAtA) - i, nil
410 +}
411 +
412 +func (m *SignedPayload) MarshalVT() (dAtA []byte, err error) {
413 + if m == nil {
414 + return nil, nil
415 + }
416 + size := m.SizeVT()
417 + dAtA = make([]byte, size)
418 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
419 + if err != nil {
420 + return nil, err
421 + }
422 + return dAtA[:n], nil
423 +}
424 +
425 +func (m *SignedPayload) MarshalToVT(dAtA []byte) (int, error) {
426 + size := m.SizeVT()
427 + return m.MarshalToSizedBufferVT(dAtA[:size])
428 +}
429 +
430 +func (m *SignedPayload) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
431 + if m == nil {
432 + return 0, nil
433 + }
434 + i := len(dAtA)
435 + _ = i
436 + var l int
437 + _ = l
438 + if m.unknownFields != nil {
439 + i -= len(m.unknownFields)
440 + copy(dAtA[i:], m.unknownFields)
441 + }
442 + if len(m.Signature) > 0 {
443 + i -= len(m.Signature)
444 + copy(dAtA[i:], m.Signature)
445 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Signature)))
446 + i--
447 + dAtA[i] = 0x12
448 + }
449 + if len(m.Data) > 0 {
450 + i -= len(m.Data)
451 + copy(dAtA[i:], m.Data)
452 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Data)))
453 + i--
454 + dAtA[i] = 0xa
455 + }
456 + return len(dAtA) - i, nil
457 +}
458 +
459 +func (m *ServerInitPayload) MarshalVT() (dAtA []byte, err error) {
460 + if m == nil {
461 + return nil, nil
462 + }
463 + size := m.SizeVT()
464 + dAtA = make([]byte, size)
465 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
466 + if err != nil {
467 + return nil, err
468 + }
469 + return dAtA[:n], nil
470 +}
471 +
472 +func (m *ServerInitPayload) MarshalToVT(dAtA []byte) (int, error) {
473 + size := m.SizeVT()
474 + return m.MarshalToSizedBufferVT(dAtA[:size])
475 +}
476 +
477 +func (m *ServerInitPayload) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
478 + if m == nil {
479 + return 0, nil
480 + }
481 + i := len(dAtA)
482 + _ = i
483 + var l int
484 + _ = l
485 + if m.unknownFields != nil {
486 + i -= len(m.unknownFields)
487 + copy(dAtA[i:], m.unknownFields)
488 + }
489 + if len(m.SessionPublicKey) > 0 {
490 + i -= len(m.SessionPublicKey)
491 + copy(dAtA[i:], m.SessionPublicKey)
492 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.SessionPublicKey)))
493 + i--
494 + dAtA[i] = 0x32
495 + }
496 + if len(m.Alpn) > 0 {
497 + i -= len(m.Alpn)
498 + copy(dAtA[i:], m.Alpn)
499 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn)))
500 + i--
501 + dAtA[i] = 0x2a
502 + }
503 + if m.Identity != nil {
504 + size, err := m.Identity.MarshalToSizedBufferVT(dAtA[:i])
505 + if err != nil {
506 + return 0, err
507 + }
508 + i -= size
509 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
510 + i--
511 + dAtA[i] = 0x22
512 + }
513 + if m.Timestamp != 0 {
514 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
515 + i--
516 + dAtA[i] = 0x18
517 + }
518 + if len(m.Nonce) > 0 {
519 + i -= len(m.Nonce)
520 + copy(dAtA[i:], m.Nonce)
521 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
522 + i--
523 + dAtA[i] = 0x12
524 + }
525 + if m.Version != 0 {
526 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Version))
527 + i--
528 + dAtA[i] = 0x8
529 + }
530 + return len(dAtA) - i, nil
531 +}
532 +
533 +func (m *EncryptedData) MarshalVT() (dAtA []byte, err error) {
534 + if m == nil {
535 + return nil, nil
536 + }
537 + size := m.SizeVT()
538 + dAtA = make([]byte, size)
539 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
540 + if err != nil {
541 + return nil, err
542 + }
543 + return dAtA[:n], nil
544 +}
545 +
546 +func (m *EncryptedData) MarshalToVT(dAtA []byte) (int, error) {
547 + size := m.SizeVT()
548 + return m.MarshalToSizedBufferVT(dAtA[:size])
549 +}
550 +
551 +func (m *EncryptedData) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
552 + if m == nil {
553 + return 0, nil
554 + }
555 + i := len(dAtA)
556 + _ = i
557 + var l int
558 + _ = l
559 + if m.unknownFields != nil {
560 + i -= len(m.unknownFields)
561 + copy(dAtA[i:], m.unknownFields)
562 + }
563 + if len(m.Payload) > 0 {
564 + i -= len(m.Payload)
565 + copy(dAtA[i:], m.Payload)
566 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Payload)))
567 + i--
568 + dAtA[i] = 0x12
569 + }
570 + if len(m.Nonce) > 0 {
571 + i -= len(m.Nonce)
572 + copy(dAtA[i:], m.Nonce)
573 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
574 + i--
575 + dAtA[i] = 0xa
576 + }
577 + return len(dAtA) - i, nil
578 +}
579 +
580 +func (m *Identity) MarshalVTStrict() (dAtA []byte, err error) {
581 + if m == nil {
582 + return nil, nil
583 + }
584 + size := m.SizeVT()
585 + dAtA = make([]byte, size)
586 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
587 + if err != nil {
588 + return nil, err
589 + }
590 + return dAtA[:n], nil
591 +}
592 +
593 +func (m *Identity) MarshalToVTStrict(dAtA []byte) (int, error) {
594 + size := m.SizeVT()
595 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
596 +}
597 +
598 +func (m *Identity) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
599 + if m == nil {
600 + return 0, nil
601 + }
602 + i := len(dAtA)
603 + _ = i
604 + var l int
605 + _ = l
606 + if m.unknownFields != nil {
607 + i -= len(m.unknownFields)
608 + copy(dAtA[i:], m.unknownFields)
609 + }
610 + if len(m.PublicKey) > 0 {
611 + i -= len(m.PublicKey)
612 + copy(dAtA[i:], m.PublicKey)
613 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.PublicKey)))
614 + i--
615 + dAtA[i] = 0x12
616 + }
617 + if len(m.Id) > 0 {
618 + i -= len(m.Id)
619 + copy(dAtA[i:], m.Id)
620 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Id)))
621 + i--
622 + dAtA[i] = 0xa
623 + }
624 + return len(dAtA) - i, nil
625 +}
626 +
627 +func (m *ClientInitPayload) MarshalVTStrict() (dAtA []byte, err error) {
628 + if m == nil {
629 + return nil, nil
630 + }
631 + size := m.SizeVT()
632 + dAtA = make([]byte, size)
633 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
634 + if err != nil {
635 + return nil, err
636 + }
637 + return dAtA[:n], nil
638 +}
639 +
640 +func (m *ClientInitPayload) MarshalToVTStrict(dAtA []byte) (int, error) {
641 + size := m.SizeVT()
642 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
643 +}
644 +
645 +func (m *ClientInitPayload) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
646 + if m == nil {
647 + return 0, nil
648 + }
649 + i := len(dAtA)
650 + _ = i
651 + var l int
652 + _ = l
653 + if m.unknownFields != nil {
654 + i -= len(m.unknownFields)
655 + copy(dAtA[i:], m.unknownFields)
656 + }
657 + if len(m.SessionPublicKey) > 0 {
658 + i -= len(m.SessionPublicKey)
659 + copy(dAtA[i:], m.SessionPublicKey)
660 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.SessionPublicKey)))
661 + i--
662 + dAtA[i] = 0x32
663 + }
664 + if len(m.Alpn) > 0 {
665 + i -= len(m.Alpn)
666 + copy(dAtA[i:], m.Alpn)
667 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn)))
668 + i--
669 + dAtA[i] = 0x2a
670 + }
671 + if m.Identity != nil {
672 + size, err := m.Identity.MarshalToSizedBufferVTStrict(dAtA[:i])
673 + if err != nil {
674 + return 0, err
675 + }
676 + i -= size
677 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
678 + i--
679 + dAtA[i] = 0x22
680 + }
681 + if m.Timestamp != 0 {
682 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
683 + i--
684 + dAtA[i] = 0x18
685 + }
686 + if len(m.Nonce) > 0 {
687 + i -= len(m.Nonce)
688 + copy(dAtA[i:], m.Nonce)
689 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
690 + i--
691 + dAtA[i] = 0x12
692 + }
693 + if m.Version != 0 {
694 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Version))
695 + i--
696 + dAtA[i] = 0x8
697 + }
698 + return len(dAtA) - i, nil
699 +}
700 +
701 +func (m *SignedPayload) MarshalVTStrict() (dAtA []byte, err error) {
702 + if m == nil {
703 + return nil, nil
704 + }
705 + size := m.SizeVT()
706 + dAtA = make([]byte, size)
707 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
708 + if err != nil {
709 + return nil, err
710 + }
711 + return dAtA[:n], nil
712 +}
713 +
714 +func (m *SignedPayload) MarshalToVTStrict(dAtA []byte) (int, error) {
715 + size := m.SizeVT()
716 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
717 +}
718 +
719 +func (m *SignedPayload) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
720 + if m == nil {
721 + return 0, nil
722 + }
723 + i := len(dAtA)
724 + _ = i
725 + var l int
726 + _ = l
727 + if m.unknownFields != nil {
728 + i -= len(m.unknownFields)
729 + copy(dAtA[i:], m.unknownFields)
730 + }
731 + if len(m.Signature) > 0 {
732 + i -= len(m.Signature)
733 + copy(dAtA[i:], m.Signature)
734 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Signature)))
735 + i--
736 + dAtA[i] = 0x12
737 + }
738 + if len(m.Data) > 0 {
739 + i -= len(m.Data)
740 + copy(dAtA[i:], m.Data)
741 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Data)))
742 + i--
743 + dAtA[i] = 0xa
744 + }
745 + return len(dAtA) - i, nil
746 +}
747 +
748 +func (m *ServerInitPayload) MarshalVTStrict() (dAtA []byte, err error) {
749 + if m == nil {
750 + return nil, nil
751 + }
752 + size := m.SizeVT()
753 + dAtA = make([]byte, size)
754 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
755 + if err != nil {
756 + return nil, err
757 + }
758 + return dAtA[:n], nil
759 +}
760 +
761 +func (m *ServerInitPayload) MarshalToVTStrict(dAtA []byte) (int, error) {
762 + size := m.SizeVT()
763 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
764 +}
765 +
766 +func (m *ServerInitPayload) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
767 + if m == nil {
768 + return 0, nil
769 + }
770 + i := len(dAtA)
771 + _ = i
772 + var l int
773 + _ = l
774 + if m.unknownFields != nil {
775 + i -= len(m.unknownFields)
776 + copy(dAtA[i:], m.unknownFields)
777 + }
778 + if len(m.SessionPublicKey) > 0 {
779 + i -= len(m.SessionPublicKey)
780 + copy(dAtA[i:], m.SessionPublicKey)
781 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.SessionPublicKey)))
782 + i--
783 + dAtA[i] = 0x32
784 + }
785 + if len(m.Alpn) > 0 {
786 + i -= len(m.Alpn)
787 + copy(dAtA[i:], m.Alpn)
788 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn)))
789 + i--
790 + dAtA[i] = 0x2a
791 + }
792 + if m.Identity != nil {
793 + size, err := m.Identity.MarshalToSizedBufferVTStrict(dAtA[:i])
794 + if err != nil {
795 + return 0, err
796 + }
797 + i -= size
798 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
799 + i--
800 + dAtA[i] = 0x22
801 + }
802 + if m.Timestamp != 0 {
803 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
804 + i--
805 + dAtA[i] = 0x18
806 + }
807 + if len(m.Nonce) > 0 {
808 + i -= len(m.Nonce)
809 + copy(dAtA[i:], m.Nonce)
810 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
811 + i--
812 + dAtA[i] = 0x12
813 + }
814 + if m.Version != 0 {
815 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Version))
816 + i--
817 + dAtA[i] = 0x8
818 + }
819 + return len(dAtA) - i, nil
820 +}
821 +
822 +func (m *EncryptedData) MarshalVTStrict() (dAtA []byte, err error) {
823 + if m == nil {
824 + return nil, nil
825 + }
826 + size := m.SizeVT()
827 + dAtA = make([]byte, size)
828 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
829 + if err != nil {
830 + return nil, err
831 + }
832 + return dAtA[:n], nil
833 +}
834 +
835 +func (m *EncryptedData) MarshalToVTStrict(dAtA []byte) (int, error) {
836 + size := m.SizeVT()
837 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
838 +}
839 +
840 +func (m *EncryptedData) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
841 + if m == nil {
842 + return 0, nil
843 + }
844 + i := len(dAtA)
845 + _ = i
846 + var l int
847 + _ = l
848 + if m.unknownFields != nil {
849 + i -= len(m.unknownFields)
850 + copy(dAtA[i:], m.unknownFields)
851 + }
852 + if len(m.Payload) > 0 {
853 + i -= len(m.Payload)
854 + copy(dAtA[i:], m.Payload)
855 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Payload)))
856 + i--
857 + dAtA[i] = 0x12
858 + }
859 + if len(m.Nonce) > 0 {
860 + i -= len(m.Nonce)
861 + copy(dAtA[i:], m.Nonce)
862 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
863 + i--
864 + dAtA[i] = 0xa
865 + }
866 + return len(dAtA) - i, nil
867 +}
868 +
869 +func (m *Identity) SizeVT() (n int) {
870 + if m == nil {
871 + return 0
872 + }
873 + var l int
874 + _ = l
875 + l = len(m.Id)
876 + if l > 0 {
877 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
878 + }
879 + l = len(m.PublicKey)
880 + if l > 0 {
881 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
882 + }
883 + n += len(m.unknownFields)
884 + return n
885 +}
886 +
887 +func (m *ClientInitPayload) SizeVT() (n int) {
888 + if m == nil {
889 + return 0
890 + }
891 + var l int
892 + _ = l
893 + if m.Version != 0 {
894 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Version))
895 + }
896 + l = len(m.Nonce)
897 + if l > 0 {
898 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
899 + }
900 + if m.Timestamp != 0 {
901 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Timestamp))
902 + }
903 + if m.Identity != nil {
904 + l = m.Identity.SizeVT()
905 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
906 + }
907 + l = len(m.Alpn)
908 + if l > 0 {
909 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
910 + }
911 + l = len(m.SessionPublicKey)
912 + if l > 0 {
913 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
914 + }
915 + n += len(m.unknownFields)
916 + return n
917 +}
918 +
919 +func (m *SignedPayload) SizeVT() (n int) {
920 + if m == nil {
921 + return 0
922 + }
923 + var l int
924 + _ = l
925 + l = len(m.Data)
926 + if l > 0 {
927 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
928 + }
929 + l = len(m.Signature)
930 + if l > 0 {
931 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
932 + }
933 + n += len(m.unknownFields)
934 + return n
935 +}
936 +
937 +func (m *ServerInitPayload) SizeVT() (n int) {
938 + if m == nil {
939 + return 0
940 + }
941 + var l int
942 + _ = l
943 + if m.Version != 0 {
944 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Version))
945 + }
946 + l = len(m.Nonce)
947 + if l > 0 {
948 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
949 + }
950 + if m.Timestamp != 0 {
951 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Timestamp))
952 + }
953 + if m.Identity != nil {
954 + l = m.Identity.SizeVT()
955 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
956 + }
957 + l = len(m.Alpn)
958 + if l > 0 {
959 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
960 + }
961 + l = len(m.SessionPublicKey)
962 + if l > 0 {
963 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
964 + }
965 + n += len(m.unknownFields)
966 + return n
967 +}
968 +
969 +func (m *EncryptedData) SizeVT() (n int) {
970 + if m == nil {
971 + return 0
972 + }
973 + var l int
974 + _ = l
975 + l = len(m.Nonce)
976 + if l > 0 {
977 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
978 + }
979 + l = len(m.Payload)
980 + if l > 0 {
981 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
982 + }
983 + n += len(m.unknownFields)
984 + return n
985 +}
986 +
987 +func (m *Identity) UnmarshalVT(dAtA []byte) error {
988 + l := len(dAtA)
989 + iNdEx := 0
990 + for iNdEx < l {
991 + preIndex := iNdEx
992 + var wire uint64
993 + for shift := uint(0); ; shift += 7 {
994 + if shift >= 64 {
995 + return protohelpers.ErrIntOverflow
996 + }
997 + if iNdEx >= l {
998 + return io.ErrUnexpectedEOF
999 + }
1000 + b := dAtA[iNdEx]
1001 + iNdEx++
1002 + wire |= uint64(b&0x7F) << shift
1003 + if b < 0x80 {
1004 + break
1005 + }
1006 + }
1007 + fieldNum := int32(wire >> 3)
1008 + wireType := int(wire & 0x7)
1009 + if wireType == 4 {
1010 + return fmt.Errorf("proto: Identity: wiretype end group for non-group")
1011 + }
1012 + if fieldNum <= 0 {
1013 + return fmt.Errorf("proto: Identity: illegal tag %d (wire type %d)", fieldNum, wire)
1014 + }
1015 + switch fieldNum {
1016 + case 1:
1017 + if wireType != 2 {
1018 + return fmt.Errorf("proto: wrong wireType = %d for field Id", wireType)
1019 + }
1020 + var stringLen uint64
1021 + for shift := uint(0); ; shift += 7 {
1022 + if shift >= 64 {
1023 + return protohelpers.ErrIntOverflow
1024 + }
1025 + if iNdEx >= l {
1026 + return io.ErrUnexpectedEOF
1027 + }
1028 + b := dAtA[iNdEx]
1029 + iNdEx++
1030 + stringLen |= uint64(b&0x7F) << shift
1031 + if b < 0x80 {
1032 + break
1033 + }
1034 + }
1035 + intStringLen := int(stringLen)
1036 + if intStringLen < 0 {
1037 + return protohelpers.ErrInvalidLength
1038 + }
1039 + postIndex := iNdEx + intStringLen
1040 + if postIndex < 0 {
1041 + return protohelpers.ErrInvalidLength
1042 + }
1043 + if postIndex > l {
1044 + return io.ErrUnexpectedEOF
1045 + }
1046 + m.Id = string(dAtA[iNdEx:postIndex])
1047 + iNdEx = postIndex
1048 + case 2:
1049 + if wireType != 2 {
1050 + return fmt.Errorf("proto: wrong wireType = %d for field PublicKey", wireType)
1051 + }
1052 + var byteLen int
1053 + for shift := uint(0); ; shift += 7 {
1054 + if shift >= 64 {
1055 + return protohelpers.ErrIntOverflow
1056 + }
1057 + if iNdEx >= l {
1058 + return io.ErrUnexpectedEOF
1059 + }
1060 + b := dAtA[iNdEx]
1061 + iNdEx++
1062 + byteLen |= int(b&0x7F) << shift
1063 + if b < 0x80 {
1064 + break
1065 + }
1066 + }
1067 + if byteLen < 0 {
1068 + return protohelpers.ErrInvalidLength
1069 + }
1070 + postIndex := iNdEx + byteLen
1071 + if postIndex < 0 {
1072 + return protohelpers.ErrInvalidLength
1073 + }
1074 + if postIndex > l {
1075 + return io.ErrUnexpectedEOF
1076 + }
1077 + m.PublicKey = append(m.PublicKey[:0], dAtA[iNdEx:postIndex]...)
1078 + if m.PublicKey == nil {
1079 + m.PublicKey = []byte{}
1080 + }
1081 + iNdEx = postIndex
1082 + default:
1083 + iNdEx = preIndex
1084 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1085 + if err != nil {
1086 + return err
1087 + }
1088 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1089 + return protohelpers.ErrInvalidLength
1090 + }
1091 + if (iNdEx + skippy) > l {
1092 + return io.ErrUnexpectedEOF
1093 + }
1094 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1095 + iNdEx += skippy
1096 + }
1097 + }
1098 +
1099 + if iNdEx > l {
1100 + return io.ErrUnexpectedEOF
1101 + }
1102 + return nil
1103 +}
1104 +func (m *ClientInitPayload) UnmarshalVT(dAtA []byte) error {
1105 + l := len(dAtA)
1106 + iNdEx := 0
1107 + for iNdEx < l {
1108 + preIndex := iNdEx
1109 + var wire uint64
1110 + for shift := uint(0); ; shift += 7 {
1111 + if shift >= 64 {
1112 + return protohelpers.ErrIntOverflow
1113 + }
1114 + if iNdEx >= l {
1115 + return io.ErrUnexpectedEOF
1116 + }
1117 + b := dAtA[iNdEx]
1118 + iNdEx++
1119 + wire |= uint64(b&0x7F) << shift
1120 + if b < 0x80 {
1121 + break
1122 + }
1123 + }
1124 + fieldNum := int32(wire >> 3)
1125 + wireType := int(wire & 0x7)
1126 + if wireType == 4 {
1127 + return fmt.Errorf("proto: ClientInitPayload: wiretype end group for non-group")
1128 + }
1129 + if fieldNum <= 0 {
1130 + return fmt.Errorf("proto: ClientInitPayload: illegal tag %d (wire type %d)", fieldNum, wire)
1131 + }
1132 + switch fieldNum {
1133 + case 1:
1134 + if wireType != 0 {
1135 + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType)
1136 + }
1137 + m.Version = 0
1138 + for shift := uint(0); ; shift += 7 {
1139 + if shift >= 64 {
1140 + return protohelpers.ErrIntOverflow
1141 + }
1142 + if iNdEx >= l {
1143 + return io.ErrUnexpectedEOF
1144 + }
1145 + b := dAtA[iNdEx]
1146 + iNdEx++
1147 + m.Version |= ProtocolVersion(b&0x7F) << shift
1148 + if b < 0x80 {
1149 + break
1150 + }
1151 + }
1152 + case 2:
1153 + if wireType != 2 {
1154 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
1155 + }
1156 + var byteLen int
1157 + for shift := uint(0); ; shift += 7 {
1158 + if shift >= 64 {
1159 + return protohelpers.ErrIntOverflow
1160 + }
1161 + if iNdEx >= l {
1162 + return io.ErrUnexpectedEOF
1163 + }
1164 + b := dAtA[iNdEx]
1165 + iNdEx++
1166 + byteLen |= int(b&0x7F) << shift
1167 + if b < 0x80 {
1168 + break
1169 + }
1170 + }
1171 + if byteLen < 0 {
1172 + return protohelpers.ErrInvalidLength
1173 + }
1174 + postIndex := iNdEx + byteLen
1175 + if postIndex < 0 {
1176 + return protohelpers.ErrInvalidLength
1177 + }
1178 + if postIndex > l {
1179 + return io.ErrUnexpectedEOF
1180 + }
1181 + m.Nonce = append(m.Nonce[:0], dAtA[iNdEx:postIndex]...)
1182 + if m.Nonce == nil {
1183 + m.Nonce = []byte{}
1184 + }
1185 + iNdEx = postIndex
1186 + case 3:
1187 + if wireType != 0 {
1188 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
1189 + }
1190 + m.Timestamp = 0
1191 + for shift := uint(0); ; shift += 7 {
1192 + if shift >= 64 {
1193 + return protohelpers.ErrIntOverflow
1194 + }
1195 + if iNdEx >= l {
1196 + return io.ErrUnexpectedEOF
1197 + }
1198 + b := dAtA[iNdEx]
1199 + iNdEx++
1200 + m.Timestamp |= int64(b&0x7F) << shift
1201 + if b < 0x80 {
1202 + break
1203 + }
1204 + }
1205 + case 4:
1206 + if wireType != 2 {
1207 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
1208 + }
1209 + var msglen int
1210 + for shift := uint(0); ; shift += 7 {
1211 + if shift >= 64 {
1212 + return protohelpers.ErrIntOverflow
1213 + }
1214 + if iNdEx >= l {
1215 + return io.ErrUnexpectedEOF
1216 + }
1217 + b := dAtA[iNdEx]
1218 + iNdEx++
1219 + msglen |= int(b&0x7F) << shift
1220 + if b < 0x80 {
1221 + break
1222 + }
1223 + }
1224 + if msglen < 0 {
1225 + return protohelpers.ErrInvalidLength
1226 + }
1227 + postIndex := iNdEx + msglen
1228 + if postIndex < 0 {
1229 + return protohelpers.ErrInvalidLength
1230 + }
1231 + if postIndex > l {
1232 + return io.ErrUnexpectedEOF
1233 + }
1234 + if m.Identity == nil {
1235 + m.Identity = &Identity{}
1236 + }
1237 + if err := m.Identity.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
1238 + return err
1239 + }
1240 + iNdEx = postIndex
1241 + case 5:
1242 + if wireType != 2 {
1243 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
1244 + }
1245 + var stringLen uint64
1246 + for shift := uint(0); ; shift += 7 {
1247 + if shift >= 64 {
1248 + return protohelpers.ErrIntOverflow
1249 + }
1250 + if iNdEx >= l {
1251 + return io.ErrUnexpectedEOF
1252 + }
1253 + b := dAtA[iNdEx]
1254 + iNdEx++
1255 + stringLen |= uint64(b&0x7F) << shift
1256 + if b < 0x80 {
1257 + break
1258 + }
1259 + }
1260 + intStringLen := int(stringLen)
1261 + if intStringLen < 0 {
1262 + return protohelpers.ErrInvalidLength
1263 + }
1264 + postIndex := iNdEx + intStringLen
1265 + if postIndex < 0 {
1266 + return protohelpers.ErrInvalidLength
1267 + }
1268 + if postIndex > l {
1269 + return io.ErrUnexpectedEOF
1270 + }
1271 + m.Alpn = string(dAtA[iNdEx:postIndex])
1272 + iNdEx = postIndex
1273 + case 6:
1274 + if wireType != 2 {
1275 + return fmt.Errorf("proto: wrong wireType = %d for field SessionPublicKey", wireType)
1276 + }
1277 + var byteLen int
1278 + for shift := uint(0); ; shift += 7 {
1279 + if shift >= 64 {
1280 + return protohelpers.ErrIntOverflow
1281 + }
1282 + if iNdEx >= l {
1283 + return io.ErrUnexpectedEOF
1284 + }
1285 + b := dAtA[iNdEx]
1286 + iNdEx++
1287 + byteLen |= int(b&0x7F) << shift
1288 + if b < 0x80 {
1289 + break
1290 + }
1291 + }
1292 + if byteLen < 0 {
1293 + return protohelpers.ErrInvalidLength
1294 + }
1295 + postIndex := iNdEx + byteLen
1296 + if postIndex < 0 {
1297 + return protohelpers.ErrInvalidLength
1298 + }
1299 + if postIndex > l {
1300 + return io.ErrUnexpectedEOF
1301 + }
1302 + m.SessionPublicKey = append(m.SessionPublicKey[:0], dAtA[iNdEx:postIndex]...)
1303 + if m.SessionPublicKey == nil {
1304 + m.SessionPublicKey = []byte{}
1305 + }
1306 + iNdEx = postIndex
1307 + default:
1308 + iNdEx = preIndex
1309 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1310 + if err != nil {
1311 + return err
1312 + }
1313 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1314 + return protohelpers.ErrInvalidLength
1315 + }
1316 + if (iNdEx + skippy) > l {
1317 + return io.ErrUnexpectedEOF
1318 + }
1319 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1320 + iNdEx += skippy
1321 + }
1322 + }
1323 +
1324 + if iNdEx > l {
1325 + return io.ErrUnexpectedEOF
1326 + }
1327 + return nil
1328 +}
1329 +func (m *SignedPayload) UnmarshalVT(dAtA []byte) error {
1330 + l := len(dAtA)
1331 + iNdEx := 0
1332 + for iNdEx < l {
1333 + preIndex := iNdEx
1334 + var wire uint64
1335 + for shift := uint(0); ; shift += 7 {
1336 + if shift >= 64 {
1337 + return protohelpers.ErrIntOverflow
1338 + }
1339 + if iNdEx >= l {
1340 + return io.ErrUnexpectedEOF
1341 + }
1342 + b := dAtA[iNdEx]
1343 + iNdEx++
1344 + wire |= uint64(b&0x7F) << shift
1345 + if b < 0x80 {
1346 + break
1347 + }
1348 + }
1349 + fieldNum := int32(wire >> 3)
1350 + wireType := int(wire & 0x7)
1351 + if wireType == 4 {
1352 + return fmt.Errorf("proto: SignedPayload: wiretype end group for non-group")
1353 + }
1354 + if fieldNum <= 0 {
1355 + return fmt.Errorf("proto: SignedPayload: illegal tag %d (wire type %d)", fieldNum, wire)
1356 + }
1357 + switch fieldNum {
1358 + case 1:
1359 + if wireType != 2 {
1360 + return fmt.Errorf("proto: wrong wireType = %d for field Data", wireType)
1361 + }
1362 + var byteLen int
1363 + for shift := uint(0); ; shift += 7 {
1364 + if shift >= 64 {
1365 + return protohelpers.ErrIntOverflow
1366 + }
1367 + if iNdEx >= l {
1368 + return io.ErrUnexpectedEOF
1369 + }
1370 + b := dAtA[iNdEx]
1371 + iNdEx++
1372 + byteLen |= int(b&0x7F) << shift
1373 + if b < 0x80 {
1374 + break
1375 + }
1376 + }
1377 + if byteLen < 0 {
1378 + return protohelpers.ErrInvalidLength
1379 + }
1380 + postIndex := iNdEx + byteLen
1381 + if postIndex < 0 {
1382 + return protohelpers.ErrInvalidLength
1383 + }
1384 + if postIndex > l {
1385 + return io.ErrUnexpectedEOF
1386 + }
1387 + m.Data = append(m.Data[:0], dAtA[iNdEx:postIndex]...)
1388 + if m.Data == nil {
1389 + m.Data = []byte{}
1390 + }
1391 + iNdEx = postIndex
1392 + case 2:
1393 + if wireType != 2 {
1394 + return fmt.Errorf("proto: wrong wireType = %d for field Signature", wireType)
1395 + }
1396 + var byteLen int
1397 + for shift := uint(0); ; shift += 7 {
1398 + if shift >= 64 {
1399 + return protohelpers.ErrIntOverflow
1400 + }
1401 + if iNdEx >= l {
1402 + return io.ErrUnexpectedEOF
1403 + }
1404 + b := dAtA[iNdEx]
1405 + iNdEx++
1406 + byteLen |= int(b&0x7F) << shift
1407 + if b < 0x80 {
1408 + break
1409 + }
1410 + }
1411 + if byteLen < 0 {
1412 + return protohelpers.ErrInvalidLength
1413 + }
1414 + postIndex := iNdEx + byteLen
1415 + if postIndex < 0 {
1416 + return protohelpers.ErrInvalidLength
1417 + }
1418 + if postIndex > l {
1419 + return io.ErrUnexpectedEOF
1420 + }
1421 + m.Signature = append(m.Signature[:0], dAtA[iNdEx:postIndex]...)
1422 + if m.Signature == nil {
1423 + m.Signature = []byte{}
1424 + }
1425 + iNdEx = postIndex
1426 + default:
1427 + iNdEx = preIndex
1428 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1429 + if err != nil {
1430 + return err
1431 + }
1432 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1433 + return protohelpers.ErrInvalidLength
1434 + }
1435 + if (iNdEx + skippy) > l {
1436 + return io.ErrUnexpectedEOF
1437 + }
1438 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1439 + iNdEx += skippy
1440 + }
1441 + }
1442 +
1443 + if iNdEx > l {
1444 + return io.ErrUnexpectedEOF
1445 + }
1446 + return nil
1447 +}
1448 +func (m *ServerInitPayload) UnmarshalVT(dAtA []byte) error {
1449 + l := len(dAtA)
1450 + iNdEx := 0
1451 + for iNdEx < l {
1452 + preIndex := iNdEx
1453 + var wire uint64
1454 + for shift := uint(0); ; shift += 7 {
1455 + if shift >= 64 {
1456 + return protohelpers.ErrIntOverflow
1457 + }
1458 + if iNdEx >= l {
1459 + return io.ErrUnexpectedEOF
1460 + }
1461 + b := dAtA[iNdEx]
1462 + iNdEx++
1463 + wire |= uint64(b&0x7F) << shift
1464 + if b < 0x80 {
1465 + break
1466 + }
1467 + }
1468 + fieldNum := int32(wire >> 3)
1469 + wireType := int(wire & 0x7)
1470 + if wireType == 4 {
1471 + return fmt.Errorf("proto: ServerInitPayload: wiretype end group for non-group")
1472 + }
1473 + if fieldNum <= 0 {
1474 + return fmt.Errorf("proto: ServerInitPayload: illegal tag %d (wire type %d)", fieldNum, wire)
1475 + }
1476 + switch fieldNum {
1477 + case 1:
1478 + if wireType != 0 {
1479 + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType)
1480 + }
1481 + m.Version = 0
1482 + for shift := uint(0); ; shift += 7 {
1483 + if shift >= 64 {
1484 + return protohelpers.ErrIntOverflow
1485 + }
1486 + if iNdEx >= l {
1487 + return io.ErrUnexpectedEOF
1488 + }
1489 + b := dAtA[iNdEx]
1490 + iNdEx++
1491 + m.Version |= ProtocolVersion(b&0x7F) << shift
1492 + if b < 0x80 {
1493 + break
1494 + }
1495 + }
1496 + case 2:
1497 + if wireType != 2 {
1498 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
1499 + }
1500 + var byteLen int
1501 + for shift := uint(0); ; shift += 7 {
1502 + if shift >= 64 {
1503 + return protohelpers.ErrIntOverflow
1504 + }
1505 + if iNdEx >= l {
1506 + return io.ErrUnexpectedEOF
1507 + }
1508 + b := dAtA[iNdEx]
1509 + iNdEx++
1510 + byteLen |= int(b&0x7F) << shift
1511 + if b < 0x80 {
1512 + break
1513 + }
1514 + }
1515 + if byteLen < 0 {
1516 + return protohelpers.ErrInvalidLength
1517 + }
1518 + postIndex := iNdEx + byteLen
1519 + if postIndex < 0 {
1520 + return protohelpers.ErrInvalidLength
1521 + }
1522 + if postIndex > l {
1523 + return io.ErrUnexpectedEOF
1524 + }
1525 + m.Nonce = append(m.Nonce[:0], dAtA[iNdEx:postIndex]...)
1526 + if m.Nonce == nil {
1527 + m.Nonce = []byte{}
1528 + }
1529 + iNdEx = postIndex
1530 + case 3:
1531 + if wireType != 0 {
1532 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
1533 + }
1534 + m.Timestamp = 0
1535 + for shift := uint(0); ; shift += 7 {
1536 + if shift >= 64 {
1537 + return protohelpers.ErrIntOverflow
1538 + }
1539 + if iNdEx >= l {
1540 + return io.ErrUnexpectedEOF
1541 + }
1542 + b := dAtA[iNdEx]
1543 + iNdEx++
1544 + m.Timestamp |= int64(b&0x7F) << shift
1545 + if b < 0x80 {
1546 + break
1547 + }
1548 + }
1549 + case 4:
1550 + if wireType != 2 {
1551 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
1552 + }
1553 + var msglen int
1554 + for shift := uint(0); ; shift += 7 {
1555 + if shift >= 64 {
1556 + return protohelpers.ErrIntOverflow
1557 + }
1558 + if iNdEx >= l {
1559 + return io.ErrUnexpectedEOF
1560 + }
1561 + b := dAtA[iNdEx]
1562 + iNdEx++
1563 + msglen |= int(b&0x7F) << shift
1564 + if b < 0x80 {
1565 + break
1566 + }
1567 + }
1568 + if msglen < 0 {
1569 + return protohelpers.ErrInvalidLength
1570 + }
1571 + postIndex := iNdEx + msglen
1572 + if postIndex < 0 {
1573 + return protohelpers.ErrInvalidLength
1574 + }
1575 + if postIndex > l {
1576 + return io.ErrUnexpectedEOF
1577 + }
1578 + if m.Identity == nil {
1579 + m.Identity = &Identity{}
1580 + }
1581 + if err := m.Identity.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
1582 + return err
1583 + }
1584 + iNdEx = postIndex
1585 + case 5:
1586 + if wireType != 2 {
1587 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
1588 + }
1589 + var stringLen uint64
1590 + for shift := uint(0); ; shift += 7 {
1591 + if shift >= 64 {
1592 + return protohelpers.ErrIntOverflow
1593 + }
1594 + if iNdEx >= l {
1595 + return io.ErrUnexpectedEOF
1596 + }
1597 + b := dAtA[iNdEx]
1598 + iNdEx++
1599 + stringLen |= uint64(b&0x7F) << shift
1600 + if b < 0x80 {
1601 + break
1602 + }
1603 + }
1604 + intStringLen := int(stringLen)
1605 + if intStringLen < 0 {
1606 + return protohelpers.ErrInvalidLength
1607 + }
1608 + postIndex := iNdEx + intStringLen
1609 + if postIndex < 0 {
1610 + return protohelpers.ErrInvalidLength
1611 + }
1612 + if postIndex > l {
1613 + return io.ErrUnexpectedEOF
1614 + }
1615 + m.Alpn = string(dAtA[iNdEx:postIndex])
1616 + iNdEx = postIndex
1617 + case 6:
1618 + if wireType != 2 {
1619 + return fmt.Errorf("proto: wrong wireType = %d for field SessionPublicKey", wireType)
1620 + }
1621 + var byteLen int
1622 + for shift := uint(0); ; shift += 7 {
1623 + if shift >= 64 {
1624 + return protohelpers.ErrIntOverflow
1625 + }
1626 + if iNdEx >= l {
1627 + return io.ErrUnexpectedEOF
1628 + }
1629 + b := dAtA[iNdEx]
1630 + iNdEx++
1631 + byteLen |= int(b&0x7F) << shift
1632 + if b < 0x80 {
1633 + break
1634 + }
1635 + }
1636 + if byteLen < 0 {
1637 + return protohelpers.ErrInvalidLength
1638 + }
1639 + postIndex := iNdEx + byteLen
1640 + if postIndex < 0 {
1641 + return protohelpers.ErrInvalidLength
1642 + }
1643 + if postIndex > l {
1644 + return io.ErrUnexpectedEOF
1645 + }
1646 + m.SessionPublicKey = append(m.SessionPublicKey[:0], dAtA[iNdEx:postIndex]...)
1647 + if m.SessionPublicKey == nil {
1648 + m.SessionPublicKey = []byte{}
1649 + }
1650 + iNdEx = postIndex
1651 + default:
1652 + iNdEx = preIndex
1653 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1654 + if err != nil {
1655 + return err
1656 + }
1657 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1658 + return protohelpers.ErrInvalidLength
1659 + }
1660 + if (iNdEx + skippy) > l {
1661 + return io.ErrUnexpectedEOF
1662 + }
1663 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1664 + iNdEx += skippy
1665 + }
1666 + }
1667 +
1668 + if iNdEx > l {
1669 + return io.ErrUnexpectedEOF
1670 + }
1671 + return nil
1672 +}
1673 +func (m *EncryptedData) UnmarshalVT(dAtA []byte) error {
1674 + l := len(dAtA)
1675 + iNdEx := 0
1676 + for iNdEx < l {
1677 + preIndex := iNdEx
1678 + var wire uint64
1679 + for shift := uint(0); ; shift += 7 {
1680 + if shift >= 64 {
1681 + return protohelpers.ErrIntOverflow
1682 + }
1683 + if iNdEx >= l {
1684 + return io.ErrUnexpectedEOF
1685 + }
1686 + b := dAtA[iNdEx]
1687 + iNdEx++
1688 + wire |= uint64(b&0x7F) << shift
1689 + if b < 0x80 {
1690 + break
1691 + }
1692 + }
1693 + fieldNum := int32(wire >> 3)
1694 + wireType := int(wire & 0x7)
1695 + if wireType == 4 {
1696 + return fmt.Errorf("proto: EncryptedData: wiretype end group for non-group")
1697 + }
1698 + if fieldNum <= 0 {
1699 + return fmt.Errorf("proto: EncryptedData: illegal tag %d (wire type %d)", fieldNum, wire)
1700 + }
1701 + switch fieldNum {
1702 + case 1:
1703 + if wireType != 2 {
1704 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
1705 + }
1706 + var byteLen int
1707 + for shift := uint(0); ; shift += 7 {
1708 + if shift >= 64 {
1709 + return protohelpers.ErrIntOverflow
1710 + }
1711 + if iNdEx >= l {
1712 + return io.ErrUnexpectedEOF
1713 + }
1714 + b := dAtA[iNdEx]
1715 + iNdEx++
1716 + byteLen |= int(b&0x7F) << shift
1717 + if b < 0x80 {
1718 + break
1719 + }
1720 + }
1721 + if byteLen < 0 {
1722 + return protohelpers.ErrInvalidLength
1723 + }
1724 + postIndex := iNdEx + byteLen
1725 + if postIndex < 0 {
1726 + return protohelpers.ErrInvalidLength
1727 + }
1728 + if postIndex > l {
1729 + return io.ErrUnexpectedEOF
1730 + }
1731 + m.Nonce = append(m.Nonce[:0], dAtA[iNdEx:postIndex]...)
1732 + if m.Nonce == nil {
1733 + m.Nonce = []byte{}
1734 + }
1735 + iNdEx = postIndex
1736 + case 2:
1737 + if wireType != 2 {
1738 + return fmt.Errorf("proto: wrong wireType = %d for field Payload", wireType)
1739 + }
1740 + var byteLen int
1741 + for shift := uint(0); ; shift += 7 {
1742 + if shift >= 64 {
1743 + return protohelpers.ErrIntOverflow
1744 + }
1745 + if iNdEx >= l {
1746 + return io.ErrUnexpectedEOF
1747 + }
1748 + b := dAtA[iNdEx]
1749 + iNdEx++
1750 + byteLen |= int(b&0x7F) << shift
1751 + if b < 0x80 {
1752 + break
1753 + }
1754 + }
1755 + if byteLen < 0 {
1756 + return protohelpers.ErrInvalidLength
1757 + }
1758 + postIndex := iNdEx + byteLen
1759 + if postIndex < 0 {
1760 + return protohelpers.ErrInvalidLength
1761 + }
1762 + if postIndex > l {
1763 + return io.ErrUnexpectedEOF
1764 + }
1765 + m.Payload = append(m.Payload[:0], dAtA[iNdEx:postIndex]...)
1766 + if m.Payload == nil {
1767 + m.Payload = []byte{}
1768 + }
1769 + iNdEx = postIndex
1770 + default:
1771 + iNdEx = preIndex
1772 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1773 + if err != nil {
1774 + return err
1775 + }
1776 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1777 + return protohelpers.ErrInvalidLength
1778 + }
1779 + if (iNdEx + skippy) > l {
1780 + return io.ErrUnexpectedEOF
1781 + }
1782 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1783 + iNdEx += skippy
1784 + }
1785 + }
1786 +
1787 + if iNdEx > l {
1788 + return io.ErrUnexpectedEOF
1789 + }
1790 + return nil
1791 +}
1792 +func (m *Identity) UnmarshalVTUnsafe(dAtA []byte) error {
1793 + l := len(dAtA)
1794 + iNdEx := 0
1795 + for iNdEx < l {
1796 + preIndex := iNdEx
1797 + var wire uint64
1798 + for shift := uint(0); ; shift += 7 {
1799 + if shift >= 64 {
1800 + return protohelpers.ErrIntOverflow
1801 + }
1802 + if iNdEx >= l {
1803 + return io.ErrUnexpectedEOF
1804 + }
1805 + b := dAtA[iNdEx]
1806 + iNdEx++
1807 + wire |= uint64(b&0x7F) << shift
1808 + if b < 0x80 {
1809 + break
1810 + }
1811 + }
1812 + fieldNum := int32(wire >> 3)
1813 + wireType := int(wire & 0x7)
1814 + if wireType == 4 {
1815 + return fmt.Errorf("proto: Identity: wiretype end group for non-group")
1816 + }
1817 + if fieldNum <= 0 {
1818 + return fmt.Errorf("proto: Identity: illegal tag %d (wire type %d)", fieldNum, wire)
1819 + }
1820 + switch fieldNum {
1821 + case 1:
1822 + if wireType != 2 {
1823 + return fmt.Errorf("proto: wrong wireType = %d for field Id", wireType)
1824 + }
1825 + var stringLen uint64
1826 + for shift := uint(0); ; shift += 7 {
1827 + if shift >= 64 {
1828 + return protohelpers.ErrIntOverflow
1829 + }
1830 + if iNdEx >= l {
1831 + return io.ErrUnexpectedEOF
1832 + }
1833 + b := dAtA[iNdEx]
1834 + iNdEx++
1835 + stringLen |= uint64(b&0x7F) << shift
1836 + if b < 0x80 {
1837 + break
1838 + }
1839 + }
1840 + intStringLen := int(stringLen)
1841 + if intStringLen < 0 {
1842 + return protohelpers.ErrInvalidLength
1843 + }
1844 + postIndex := iNdEx + intStringLen
1845 + if postIndex < 0 {
1846 + return protohelpers.ErrInvalidLength
1847 + }
1848 + if postIndex > l {
1849 + return io.ErrUnexpectedEOF
1850 + }
1851 + var stringValue string
1852 + if intStringLen > 0 {
1853 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
1854 + }
1855 + m.Id = stringValue
1856 + iNdEx = postIndex
1857 + case 2:
1858 + if wireType != 2 {
1859 + return fmt.Errorf("proto: wrong wireType = %d for field PublicKey", wireType)
1860 + }
1861 + var byteLen int
1862 + for shift := uint(0); ; shift += 7 {
1863 + if shift >= 64 {
1864 + return protohelpers.ErrIntOverflow
1865 + }
1866 + if iNdEx >= l {
1867 + return io.ErrUnexpectedEOF
1868 + }
1869 + b := dAtA[iNdEx]
1870 + iNdEx++
1871 + byteLen |= int(b&0x7F) << shift
1872 + if b < 0x80 {
1873 + break
1874 + }
1875 + }
1876 + if byteLen < 0 {
1877 + return protohelpers.ErrInvalidLength
1878 + }
1879 + postIndex := iNdEx + byteLen
1880 + if postIndex < 0 {
1881 + return protohelpers.ErrInvalidLength
1882 + }
1883 + if postIndex > l {
1884 + return io.ErrUnexpectedEOF
1885 + }
1886 + m.PublicKey = dAtA[iNdEx:postIndex]
1887 + iNdEx = postIndex
1888 + default:
1889 + iNdEx = preIndex
1890 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1891 + if err != nil {
1892 + return err
1893 + }
1894 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1895 + return protohelpers.ErrInvalidLength
1896 + }
1897 + if (iNdEx + skippy) > l {
1898 + return io.ErrUnexpectedEOF
1899 + }
1900 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1901 + iNdEx += skippy
1902 + }
1903 + }
1904 +
1905 + if iNdEx > l {
1906 + return io.ErrUnexpectedEOF
1907 + }
1908 + return nil
1909 +}
1910 +func (m *ClientInitPayload) UnmarshalVTUnsafe(dAtA []byte) error {
1911 + l := len(dAtA)
1912 + iNdEx := 0
1913 + for iNdEx < l {
1914 + preIndex := iNdEx
1915 + var wire uint64
1916 + for shift := uint(0); ; shift += 7 {
1917 + if shift >= 64 {
1918 + return protohelpers.ErrIntOverflow
1919 + }
1920 + if iNdEx >= l {
1921 + return io.ErrUnexpectedEOF
1922 + }
1923 + b := dAtA[iNdEx]
1924 + iNdEx++
1925 + wire |= uint64(b&0x7F) << shift
1926 + if b < 0x80 {
1927 + break
1928 + }
1929 + }
1930 + fieldNum := int32(wire >> 3)
1931 + wireType := int(wire & 0x7)
1932 + if wireType == 4 {
1933 + return fmt.Errorf("proto: ClientInitPayload: wiretype end group for non-group")
1934 + }
1935 + if fieldNum <= 0 {
1936 + return fmt.Errorf("proto: ClientInitPayload: illegal tag %d (wire type %d)", fieldNum, wire)
1937 + }
1938 + switch fieldNum {
1939 + case 1:
1940 + if wireType != 0 {
1941 + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType)
1942 + }
1943 + m.Version = 0
1944 + for shift := uint(0); ; shift += 7 {
1945 + if shift >= 64 {
1946 + return protohelpers.ErrIntOverflow
1947 + }
1948 + if iNdEx >= l {
1949 + return io.ErrUnexpectedEOF
1950 + }
1951 + b := dAtA[iNdEx]
1952 + iNdEx++
1953 + m.Version |= ProtocolVersion(b&0x7F) << shift
1954 + if b < 0x80 {
1955 + break
1956 + }
1957 + }
1958 + case 2:
1959 + if wireType != 2 {
1960 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
1961 + }
1962 + var byteLen int
1963 + for shift := uint(0); ; shift += 7 {
1964 + if shift >= 64 {
1965 + return protohelpers.ErrIntOverflow
1966 + }
1967 + if iNdEx >= l {
1968 + return io.ErrUnexpectedEOF
1969 + }
1970 + b := dAtA[iNdEx]
1971 + iNdEx++
1972 + byteLen |= int(b&0x7F) << shift
1973 + if b < 0x80 {
1974 + break
1975 + }
1976 + }
1977 + if byteLen < 0 {
1978 + return protohelpers.ErrInvalidLength
1979 + }
1980 + postIndex := iNdEx + byteLen
1981 + if postIndex < 0 {
1982 + return protohelpers.ErrInvalidLength
1983 + }
1984 + if postIndex > l {
1985 + return io.ErrUnexpectedEOF
1986 + }
1987 + m.Nonce = dAtA[iNdEx:postIndex]
1988 + iNdEx = postIndex
1989 + case 3:
1990 + if wireType != 0 {
1991 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
1992 + }
1993 + m.Timestamp = 0
1994 + for shift := uint(0); ; shift += 7 {
1995 + if shift >= 64 {
1996 + return protohelpers.ErrIntOverflow
1997 + }
1998 + if iNdEx >= l {
1999 + return io.ErrUnexpectedEOF
2000 + }
2001 + b := dAtA[iNdEx]
2002 + iNdEx++
2003 + m.Timestamp |= int64(b&0x7F) << shift
2004 + if b < 0x80 {
2005 + break
2006 + }
2007 + }
2008 + case 4:
2009 + if wireType != 2 {
2010 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
2011 + }
2012 + var msglen int
2013 + for shift := uint(0); ; shift += 7 {
2014 + if shift >= 64 {
2015 + return protohelpers.ErrIntOverflow
2016 + }
2017 + if iNdEx >= l {
2018 + return io.ErrUnexpectedEOF
2019 + }
2020 + b := dAtA[iNdEx]
2021 + iNdEx++
2022 + msglen |= int(b&0x7F) << shift
2023 + if b < 0x80 {
2024 + break
2025 + }
2026 + }
2027 + if msglen < 0 {
2028 + return protohelpers.ErrInvalidLength
2029 + }
2030 + postIndex := iNdEx + msglen
2031 + if postIndex < 0 {
2032 + return protohelpers.ErrInvalidLength
2033 + }
2034 + if postIndex > l {
2035 + return io.ErrUnexpectedEOF
2036 + }
2037 + if m.Identity == nil {
2038 + m.Identity = &Identity{}
2039 + }
2040 + if err := m.Identity.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
2041 + return err
2042 + }
2043 + iNdEx = postIndex
2044 + case 5:
2045 + if wireType != 2 {
2046 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
2047 + }
2048 + var stringLen uint64
2049 + for shift := uint(0); ; shift += 7 {
2050 + if shift >= 64 {
2051 + return protohelpers.ErrIntOverflow
2052 + }
2053 + if iNdEx >= l {
2054 + return io.ErrUnexpectedEOF
2055 + }
2056 + b := dAtA[iNdEx]
2057 + iNdEx++
2058 + stringLen |= uint64(b&0x7F) << shift
2059 + if b < 0x80 {
2060 + break
2061 + }
2062 + }
2063 + intStringLen := int(stringLen)
2064 + if intStringLen < 0 {
2065 + return protohelpers.ErrInvalidLength
2066 + }
2067 + postIndex := iNdEx + intStringLen
2068 + if postIndex < 0 {
2069 + return protohelpers.ErrInvalidLength
2070 + }
2071 + if postIndex > l {
2072 + return io.ErrUnexpectedEOF
2073 + }
2074 + var stringValue string
2075 + if intStringLen > 0 {
2076 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
2077 + }
2078 + m.Alpn = stringValue
2079 + iNdEx = postIndex
2080 + case 6:
2081 + if wireType != 2 {
2082 + return fmt.Errorf("proto: wrong wireType = %d for field SessionPublicKey", wireType)
2083 + }
2084 + var byteLen int
2085 + for shift := uint(0); ; shift += 7 {
2086 + if shift >= 64 {
2087 + return protohelpers.ErrIntOverflow
2088 + }
2089 + if iNdEx >= l {
2090 + return io.ErrUnexpectedEOF
2091 + }
2092 + b := dAtA[iNdEx]
2093 + iNdEx++
2094 + byteLen |= int(b&0x7F) << shift
2095 + if b < 0x80 {
2096 + break
2097 + }
2098 + }
2099 + if byteLen < 0 {
2100 + return protohelpers.ErrInvalidLength
2101 + }
2102 + postIndex := iNdEx + byteLen
2103 + if postIndex < 0 {
2104 + return protohelpers.ErrInvalidLength
2105 + }
2106 + if postIndex > l {
2107 + return io.ErrUnexpectedEOF
2108 + }
2109 + m.SessionPublicKey = dAtA[iNdEx:postIndex]
2110 + iNdEx = postIndex
2111 + default:
2112 + iNdEx = preIndex
2113 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2114 + if err != nil {
2115 + return err
2116 + }
2117 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2118 + return protohelpers.ErrInvalidLength
2119 + }
2120 + if (iNdEx + skippy) > l {
2121 + return io.ErrUnexpectedEOF
2122 + }
2123 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2124 + iNdEx += skippy
2125 + }
2126 + }
2127 +
2128 + if iNdEx > l {
2129 + return io.ErrUnexpectedEOF
2130 + }
2131 + return nil
2132 +}
2133 +func (m *SignedPayload) UnmarshalVTUnsafe(dAtA []byte) error {
2134 + l := len(dAtA)
2135 + iNdEx := 0
2136 + for iNdEx < l {
2137 + preIndex := iNdEx
2138 + var wire uint64
2139 + for shift := uint(0); ; shift += 7 {
2140 + if shift >= 64 {
2141 + return protohelpers.ErrIntOverflow
2142 + }
2143 + if iNdEx >= l {
2144 + return io.ErrUnexpectedEOF
2145 + }
2146 + b := dAtA[iNdEx]
2147 + iNdEx++
2148 + wire |= uint64(b&0x7F) << shift
2149 + if b < 0x80 {
2150 + break
2151 + }
2152 + }
2153 + fieldNum := int32(wire >> 3)
2154 + wireType := int(wire & 0x7)
2155 + if wireType == 4 {
2156 + return fmt.Errorf("proto: SignedPayload: wiretype end group for non-group")
2157 + }
2158 + if fieldNum <= 0 {
2159 + return fmt.Errorf("proto: SignedPayload: illegal tag %d (wire type %d)", fieldNum, wire)
2160 + }
2161 + switch fieldNum {
2162 + case 1:
2163 + if wireType != 2 {
2164 + return fmt.Errorf("proto: wrong wireType = %d for field Data", wireType)
2165 + }
2166 + var byteLen int
2167 + for shift := uint(0); ; shift += 7 {
2168 + if shift >= 64 {
2169 + return protohelpers.ErrIntOverflow
2170 + }
2171 + if iNdEx >= l {
2172 + return io.ErrUnexpectedEOF
2173 + }
2174 + b := dAtA[iNdEx]
2175 + iNdEx++
2176 + byteLen |= int(b&0x7F) << shift
2177 + if b < 0x80 {
2178 + break
2179 + }
2180 + }
2181 + if byteLen < 0 {
2182 + return protohelpers.ErrInvalidLength
2183 + }
2184 + postIndex := iNdEx + byteLen
2185 + if postIndex < 0 {
2186 + return protohelpers.ErrInvalidLength
2187 + }
2188 + if postIndex > l {
2189 + return io.ErrUnexpectedEOF
2190 + }
2191 + m.Data = dAtA[iNdEx:postIndex]
2192 + iNdEx = postIndex
2193 + case 2:
2194 + if wireType != 2 {
2195 + return fmt.Errorf("proto: wrong wireType = %d for field Signature", wireType)
2196 + }
2197 + var byteLen int
2198 + for shift := uint(0); ; shift += 7 {
2199 + if shift >= 64 {
2200 + return protohelpers.ErrIntOverflow
2201 + }
2202 + if iNdEx >= l {
2203 + return io.ErrUnexpectedEOF
2204 + }
2205 + b := dAtA[iNdEx]
2206 + iNdEx++
2207 + byteLen |= int(b&0x7F) << shift
2208 + if b < 0x80 {
2209 + break
2210 + }
2211 + }
2212 + if byteLen < 0 {
2213 + return protohelpers.ErrInvalidLength
2214 + }
2215 + postIndex := iNdEx + byteLen
2216 + if postIndex < 0 {
2217 + return protohelpers.ErrInvalidLength
2218 + }
2219 + if postIndex > l {
2220 + return io.ErrUnexpectedEOF
2221 + }
2222 + m.Signature = dAtA[iNdEx:postIndex]
2223 + iNdEx = postIndex
2224 + default:
2225 + iNdEx = preIndex
2226 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2227 + if err != nil {
2228 + return err
2229 + }
2230 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2231 + return protohelpers.ErrInvalidLength
2232 + }
2233 + if (iNdEx + skippy) > l {
2234 + return io.ErrUnexpectedEOF
2235 + }
2236 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2237 + iNdEx += skippy
2238 + }
2239 + }
2240 +
2241 + if iNdEx > l {
2242 + return io.ErrUnexpectedEOF
2243 + }
2244 + return nil
2245 +}
2246 +func (m *ServerInitPayload) UnmarshalVTUnsafe(dAtA []byte) error {
2247 + l := len(dAtA)
2248 + iNdEx := 0
2249 + for iNdEx < l {
2250 + preIndex := iNdEx
2251 + var wire uint64
2252 + for shift := uint(0); ; shift += 7 {
2253 + if shift >= 64 {
2254 + return protohelpers.ErrIntOverflow
2255 + }
2256 + if iNdEx >= l {
2257 + return io.ErrUnexpectedEOF
2258 + }
2259 + b := dAtA[iNdEx]
2260 + iNdEx++
2261 + wire |= uint64(b&0x7F) << shift
2262 + if b < 0x80 {
2263 + break
2264 + }
2265 + }
2266 + fieldNum := int32(wire >> 3)
2267 + wireType := int(wire & 0x7)
2268 + if wireType == 4 {
2269 + return fmt.Errorf("proto: ServerInitPayload: wiretype end group for non-group")
2270 + }
2271 + if fieldNum <= 0 {
2272 + return fmt.Errorf("proto: ServerInitPayload: illegal tag %d (wire type %d)", fieldNum, wire)
2273 + }
2274 + switch fieldNum {
2275 + case 1:
2276 + if wireType != 0 {
2277 + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType)
2278 + }
2279 + m.Version = 0
2280 + for shift := uint(0); ; shift += 7 {
2281 + if shift >= 64 {
2282 + return protohelpers.ErrIntOverflow
2283 + }
2284 + if iNdEx >= l {
2285 + return io.ErrUnexpectedEOF
2286 + }
2287 + b := dAtA[iNdEx]
2288 + iNdEx++
2289 + m.Version |= ProtocolVersion(b&0x7F) << shift
2290 + if b < 0x80 {
2291 + break
2292 + }
2293 + }
2294 + case 2:
2295 + if wireType != 2 {
2296 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
2297 + }
2298 + var byteLen int
2299 + for shift := uint(0); ; shift += 7 {
2300 + if shift >= 64 {
2301 + return protohelpers.ErrIntOverflow
2302 + }
2303 + if iNdEx >= l {
2304 + return io.ErrUnexpectedEOF
2305 + }
2306 + b := dAtA[iNdEx]
2307 + iNdEx++
2308 + byteLen |= int(b&0x7F) << shift
2309 + if b < 0x80 {
2310 + break
2311 + }
2312 + }
2313 + if byteLen < 0 {
2314 + return protohelpers.ErrInvalidLength
2315 + }
2316 + postIndex := iNdEx + byteLen
2317 + if postIndex < 0 {
2318 + return protohelpers.ErrInvalidLength
2319 + }
2320 + if postIndex > l {
2321 + return io.ErrUnexpectedEOF
2322 + }
2323 + m.Nonce = dAtA[iNdEx:postIndex]
2324 + iNdEx = postIndex
2325 + case 3:
2326 + if wireType != 0 {
2327 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
2328 + }
2329 + m.Timestamp = 0
2330 + for shift := uint(0); ; shift += 7 {
2331 + if shift >= 64 {
2332 + return protohelpers.ErrIntOverflow
2333 + }
2334 + if iNdEx >= l {
2335 + return io.ErrUnexpectedEOF
2336 + }
2337 + b := dAtA[iNdEx]
2338 + iNdEx++
2339 + m.Timestamp |= int64(b&0x7F) << shift
2340 + if b < 0x80 {
2341 + break
2342 + }
2343 + }
2344 + case 4:
2345 + if wireType != 2 {
2346 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
2347 + }
2348 + var msglen int
2349 + for shift := uint(0); ; shift += 7 {
2350 + if shift >= 64 {
2351 + return protohelpers.ErrIntOverflow
2352 + }
2353 + if iNdEx >= l {
2354 + return io.ErrUnexpectedEOF
2355 + }
2356 + b := dAtA[iNdEx]
2357 + iNdEx++
2358 + msglen |= int(b&0x7F) << shift
2359 + if b < 0x80 {
2360 + break
2361 + }
2362 + }
2363 + if msglen < 0 {
2364 + return protohelpers.ErrInvalidLength
2365 + }
2366 + postIndex := iNdEx + msglen
2367 + if postIndex < 0 {
2368 + return protohelpers.ErrInvalidLength
2369 + }
2370 + if postIndex > l {
2371 + return io.ErrUnexpectedEOF
2372 + }
2373 + if m.Identity == nil {
2374 + m.Identity = &Identity{}
2375 + }
2376 + if err := m.Identity.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
2377 + return err
2378 + }
2379 + iNdEx = postIndex
2380 + case 5:
2381 + if wireType != 2 {
2382 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
2383 + }
2384 + var stringLen uint64
2385 + for shift := uint(0); ; shift += 7 {
2386 + if shift >= 64 {
2387 + return protohelpers.ErrIntOverflow
2388 + }
2389 + if iNdEx >= l {
2390 + return io.ErrUnexpectedEOF
2391 + }
2392 + b := dAtA[iNdEx]
2393 + iNdEx++
2394 + stringLen |= uint64(b&0x7F) << shift
2395 + if b < 0x80 {
2396 + break
2397 + }
2398 + }
2399 + intStringLen := int(stringLen)
2400 + if intStringLen < 0 {
2401 + return protohelpers.ErrInvalidLength
2402 + }
2403 + postIndex := iNdEx + intStringLen
2404 + if postIndex < 0 {
2405 + return protohelpers.ErrInvalidLength
2406 + }
2407 + if postIndex > l {
2408 + return io.ErrUnexpectedEOF
2409 + }
2410 + var stringValue string
2411 + if intStringLen > 0 {
2412 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
2413 + }
2414 + m.Alpn = stringValue
2415 + iNdEx = postIndex
2416 + case 6:
2417 + if wireType != 2 {
2418 + return fmt.Errorf("proto: wrong wireType = %d for field SessionPublicKey", wireType)
2419 + }
2420 + var byteLen int
2421 + for shift := uint(0); ; shift += 7 {
2422 + if shift >= 64 {
2423 + return protohelpers.ErrIntOverflow
2424 + }
2425 + if iNdEx >= l {
2426 + return io.ErrUnexpectedEOF
2427 + }
2428 + b := dAtA[iNdEx]
2429 + iNdEx++
2430 + byteLen |= int(b&0x7F) << shift
2431 + if b < 0x80 {
2432 + break
2433 + }
2434 + }
2435 + if byteLen < 0 {
2436 + return protohelpers.ErrInvalidLength
2437 + }
2438 + postIndex := iNdEx + byteLen
2439 + if postIndex < 0 {
2440 + return protohelpers.ErrInvalidLength
2441 + }
2442 + if postIndex > l {
2443 + return io.ErrUnexpectedEOF
2444 + }
2445 + m.SessionPublicKey = dAtA[iNdEx:postIndex]
2446 + iNdEx = postIndex
2447 + default:
2448 + iNdEx = preIndex
2449 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2450 + if err != nil {
2451 + return err
2452 + }
2453 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2454 + return protohelpers.ErrInvalidLength
2455 + }
2456 + if (iNdEx + skippy) > l {
2457 + return io.ErrUnexpectedEOF
2458 + }
2459 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2460 + iNdEx += skippy
2461 + }
2462 + }
2463 +
2464 + if iNdEx > l {
2465 + return io.ErrUnexpectedEOF
2466 + }
2467 + return nil
2468 +}
2469 +func (m *EncryptedData) UnmarshalVTUnsafe(dAtA []byte) error {
2470 + l := len(dAtA)
2471 + iNdEx := 0
2472 + for iNdEx < l {
2473 + preIndex := iNdEx
2474 + var wire uint64
2475 + for shift := uint(0); ; shift += 7 {
2476 + if shift >= 64 {
2477 + return protohelpers.ErrIntOverflow
2478 + }
2479 + if iNdEx >= l {
2480 + return io.ErrUnexpectedEOF
2481 + }
2482 + b := dAtA[iNdEx]
2483 + iNdEx++
2484 + wire |= uint64(b&0x7F) << shift
2485 + if b < 0x80 {
2486 + break
2487 + }
2488 + }
2489 + fieldNum := int32(wire >> 3)
2490 + wireType := int(wire & 0x7)
2491 + if wireType == 4 {
2492 + return fmt.Errorf("proto: EncryptedData: wiretype end group for non-group")
2493 + }
2494 + if fieldNum <= 0 {
2495 + return fmt.Errorf("proto: EncryptedData: illegal tag %d (wire type %d)", fieldNum, wire)
2496 + }
2497 + switch fieldNum {
2498 + case 1:
2499 + if wireType != 2 {
2500 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
2501 + }
2502 + var byteLen int
2503 + for shift := uint(0); ; shift += 7 {
2504 + if shift >= 64 {
2505 + return protohelpers.ErrIntOverflow
2506 + }
2507 + if iNdEx >= l {
2508 + return io.ErrUnexpectedEOF
2509 + }
2510 + b := dAtA[iNdEx]
2511 + iNdEx++
2512 + byteLen |= int(b&0x7F) << shift
2513 + if b < 0x80 {
2514 + break
2515 + }
2516 + }
2517 + if byteLen < 0 {
2518 + return protohelpers.ErrInvalidLength
2519 + }
2520 + postIndex := iNdEx + byteLen
2521 + if postIndex < 0 {
2522 + return protohelpers.ErrInvalidLength
2523 + }
2524 + if postIndex > l {
2525 + return io.ErrUnexpectedEOF
2526 + }
2527 + m.Nonce = dAtA[iNdEx:postIndex]
2528 + iNdEx = postIndex
2529 + case 2:
2530 + if wireType != 2 {
2531 + return fmt.Errorf("proto: wrong wireType = %d for field Payload", wireType)
2532 + }
2533 + var byteLen int
2534 + for shift := uint(0); ; shift += 7 {
2535 + if shift >= 64 {
2536 + return protohelpers.ErrIntOverflow
2537 + }
2538 + if iNdEx >= l {
2539 + return io.ErrUnexpectedEOF
2540 + }
2541 + b := dAtA[iNdEx]
2542 + iNdEx++
2543 + byteLen |= int(b&0x7F) << shift
2544 + if b < 0x80 {
2545 + break
2546 + }
2547 + }
2548 + if byteLen < 0 {
2549 + return protohelpers.ErrInvalidLength
2550 + }
2551 + postIndex := iNdEx + byteLen
2552 + if postIndex < 0 {
2553 + return protohelpers.ErrInvalidLength
2554 + }
2555 + if postIndex > l {
2556 + return io.ErrUnexpectedEOF
2557 + }
2558 + m.Payload = dAtA[iNdEx:postIndex]
2559 + iNdEx = postIndex
2560 + default:
2561 + iNdEx = preIndex
2562 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2563 + if err != nil {
2564 + return err
2565 + }
2566 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2567 + return protohelpers.ErrInvalidLength
2568 + }
2569 + if (iNdEx + skippy) > l {
2570 + return io.ErrUnexpectedEOF
2571 + }
2572 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2573 + iNdEx += skippy
2574 + }
2575 + }
2576 +
2577 + if iNdEx > l {
2578 + return io.ErrUnexpectedEOF
2579 + }
2580 + return nil
2581 +}
relaydns/core/proto/rdverb/rdverb.pb.go new
+840
@@ -0,0 +1,840 @@
1 +// Code generated by protoc-gen-go. DO NOT EDIT.
2 +// versions:
3 +// protoc-gen-go v1.36.10
4 +// protoc (unknown)
5 +// source: relaydns/core/proto/rdverb/rdverb.proto
6 +
7 +package rdverb
8 +
9 +import (
10 + rdsec "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
11 + protoreflect "google.golang.org/protobuf/reflect/protoreflect"
12 + protoimpl "google.golang.org/protobuf/runtime/protoimpl"
13 + reflect "reflect"
14 + sync "sync"
15 + unsafe "unsafe"
16 +)
17 +
18 +const (
19 + // Verify that this generated code is sufficiently up-to-date.
20 + _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
21 + // Verify that runtime/protoimpl is sufficiently up-to-date.
22 + _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
23 +)
24 +
25 +type PacketType int32
26 +
27 +const (
28 + PacketType_PACKET_TYPE_RELAY_INFO_REQUEST PacketType = 0
29 + PacketType_PACKET_TYPE_RELAY_INFO_RESPONSE PacketType = 1
30 + PacketType_PACKET_TYPE_LEASE_UPDATE_REQUEST PacketType = 2 // Authenticated
31 + PacketType_PACKET_TYPE_LEASE_UPDATE_RESPONSE PacketType = 3
32 + PacketType_PACKET_TYPE_LEASE_DELETE_REQUEST PacketType = 4 // Authenticated
33 + PacketType_PACKET_TYPE_LEASE_DELETE_RESPONSE PacketType = 5
34 + PacketType_PACKET_TYPE_CONNECTION_REQUEST PacketType = 6
35 + PacketType_PACKET_TYPE_CONNECTION_RESPONSE PacketType = 7
36 +)
37 +
38 +// Enum value maps for PacketType.
39 +var (
40 + PacketType_name = map[int32]string{
41 + 0: "PACKET_TYPE_RELAY_INFO_REQUEST",
42 + 1: "PACKET_TYPE_RELAY_INFO_RESPONSE",
43 + 2: "PACKET_TYPE_LEASE_UPDATE_REQUEST",
44 + 3: "PACKET_TYPE_LEASE_UPDATE_RESPONSE",
45 + 4: "PACKET_TYPE_LEASE_DELETE_REQUEST",
46 + 5: "PACKET_TYPE_LEASE_DELETE_RESPONSE",
47 + 6: "PACKET_TYPE_CONNECTION_REQUEST",
48 + 7: "PACKET_TYPE_CONNECTION_RESPONSE",
49 + }
50 + PacketType_value = map[string]int32{
51 + "PACKET_TYPE_RELAY_INFO_REQUEST": 0,
52 + "PACKET_TYPE_RELAY_INFO_RESPONSE": 1,
53 + "PACKET_TYPE_LEASE_UPDATE_REQUEST": 2,
54 + "PACKET_TYPE_LEASE_UPDATE_RESPONSE": 3,
55 + "PACKET_TYPE_LEASE_DELETE_REQUEST": 4,
56 + "PACKET_TYPE_LEASE_DELETE_RESPONSE": 5,
57 + "PACKET_TYPE_CONNECTION_REQUEST": 6,
58 + "PACKET_TYPE_CONNECTION_RESPONSE": 7,
59 + }
60 +)
61 +
62 +func (x PacketType) Enum() *PacketType {
63 + p := new(PacketType)
64 + *p = x
65 + return p
66 +}
67 +
68 +func (x PacketType) String() string {
69 + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
70 +}
71 +
72 +func (PacketType) Descriptor() protoreflect.EnumDescriptor {
73 + return file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes[0].Descriptor()
74 +}
75 +
76 +func (PacketType) Type() protoreflect.EnumType {
77 + return &file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes[0]
78 +}
79 +
80 +func (x PacketType) Number() protoreflect.EnumNumber {
81 + return protoreflect.EnumNumber(x)
82 +}
83 +
84 +// Deprecated: Use PacketType.Descriptor instead.
85 +func (PacketType) EnumDescriptor() ([]byte, []int) {
86 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{0}
87 +}
88 +
89 +type ResponseCode int32
90 +
91 +const (
92 + ResponseCode_RESPONSE_CODE_ACCEPTED ResponseCode = 0
93 + ResponseCode_RESPONSE_CODE_INVALID_EXPIRES ResponseCode = 1
94 + ResponseCode_RESPONSE_CODE_INVALID_IDENTITY ResponseCode = 2
95 + ResponseCode_RESPONSE_CODE_INVALID_NAME ResponseCode = 3
96 + ResponseCode_RESPONSE_CODE_INVALID_ALPN ResponseCode = 4
97 + ResponseCode_RESPONSE_CODE_REJECTED ResponseCode = 5
98 +)
99 +
100 +// Enum value maps for ResponseCode.
101 +var (
102 + ResponseCode_name = map[int32]string{
103 + 0: "RESPONSE_CODE_ACCEPTED",
104 + 1: "RESPONSE_CODE_INVALID_EXPIRES",
105 + 2: "RESPONSE_CODE_INVALID_IDENTITY",
106 + 3: "RESPONSE_CODE_INVALID_NAME",
107 + 4: "RESPONSE_CODE_INVALID_ALPN",
108 + 5: "RESPONSE_CODE_REJECTED",
109 + }
110 + ResponseCode_value = map[string]int32{
111 + "RESPONSE_CODE_ACCEPTED": 0,
112 + "RESPONSE_CODE_INVALID_EXPIRES": 1,
113 + "RESPONSE_CODE_INVALID_IDENTITY": 2,
114 + "RESPONSE_CODE_INVALID_NAME": 3,
115 + "RESPONSE_CODE_INVALID_ALPN": 4,
116 + "RESPONSE_CODE_REJECTED": 5,
117 + }
118 +)
119 +
120 +func (x ResponseCode) Enum() *ResponseCode {
121 + p := new(ResponseCode)
122 + *p = x
123 + return p
124 +}
125 +
126 +func (x ResponseCode) String() string {
127 + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
128 +}
129 +
130 +func (ResponseCode) Descriptor() protoreflect.EnumDescriptor {
131 + return file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes[1].Descriptor()
132 +}
133 +
134 +func (ResponseCode) Type() protoreflect.EnumType {
135 + return &file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes[1]
136 +}
137 +
138 +func (x ResponseCode) Number() protoreflect.EnumNumber {
139 + return protoreflect.EnumNumber(x)
140 +}
141 +
142 +// Deprecated: Use ResponseCode.Descriptor instead.
143 +func (ResponseCode) EnumDescriptor() ([]byte, []int) {
144 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{1}
145 +}
146 +
147 +type Packet struct {
148 + state protoimpl.MessageState `protogen:"open.v1"`
149 + Type PacketType `protobuf:"varint,1,opt,name=type,proto3,enum=rdverb.PacketType" json:"type,omitempty"`
150 + Payload []byte `protobuf:"bytes,2,opt,name=payload,proto3" json:"payload,omitempty"`
151 + unknownFields protoimpl.UnknownFields
152 + sizeCache protoimpl.SizeCache
153 +}
154 +
155 +func (x *Packet) Reset() {
156 + *x = Packet{}
157 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[0]
158 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
159 + ms.StoreMessageInfo(mi)
160 +}
161 +
162 +func (x *Packet) String() string {
163 + return protoimpl.X.MessageStringOf(x)
164 +}
165 +
166 +func (*Packet) ProtoMessage() {}
167 +
168 +func (x *Packet) ProtoReflect() protoreflect.Message {
169 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[0]
170 + if x != nil {
171 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
172 + if ms.LoadMessageInfo() == nil {
173 + ms.StoreMessageInfo(mi)
174 + }
175 + return ms
176 + }
177 + return mi.MessageOf(x)
178 +}
179 +
180 +// Deprecated: Use Packet.ProtoReflect.Descriptor instead.
181 +func (*Packet) Descriptor() ([]byte, []int) {
182 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{0}
183 +}
184 +
185 +func (x *Packet) GetType() PacketType {
186 + if x != nil {
187 + return x.Type
188 + }
189 + return PacketType_PACKET_TYPE_RELAY_INFO_REQUEST
190 +}
191 +
192 +func (x *Packet) GetPayload() []byte {
193 + if x != nil {
194 + return x.Payload
195 + }
196 + return nil
197 +}
198 +
199 +type RelayInfo struct {
200 + state protoimpl.MessageState `protogen:"open.v1"`
201 + Identity *rdsec.Identity `protobuf:"bytes,1,opt,name=identity,proto3" json:"identity,omitempty"`
202 + Address []string `protobuf:"bytes,2,rep,name=address,proto3" json:"address,omitempty"`
203 + Leases []string `protobuf:"bytes,3,rep,name=leases,proto3" json:"leases,omitempty"`
204 + unknownFields protoimpl.UnknownFields
205 + sizeCache protoimpl.SizeCache
206 +}
207 +
208 +func (x *RelayInfo) Reset() {
209 + *x = RelayInfo{}
210 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[1]
211 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
212 + ms.StoreMessageInfo(mi)
213 +}
214 +
215 +func (x *RelayInfo) String() string {
216 + return protoimpl.X.MessageStringOf(x)
217 +}
218 +
219 +func (*RelayInfo) ProtoMessage() {}
220 +
221 +func (x *RelayInfo) ProtoReflect() protoreflect.Message {
222 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[1]
223 + if x != nil {
224 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
225 + if ms.LoadMessageInfo() == nil {
226 + ms.StoreMessageInfo(mi)
227 + }
228 + return ms
229 + }
230 + return mi.MessageOf(x)
231 +}
232 +
233 +// Deprecated: Use RelayInfo.ProtoReflect.Descriptor instead.
234 +func (*RelayInfo) Descriptor() ([]byte, []int) {
235 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{1}
236 +}
237 +
238 +func (x *RelayInfo) GetIdentity() *rdsec.Identity {
239 + if x != nil {
240 + return x.Identity
241 + }
242 + return nil
243 +}
244 +
245 +func (x *RelayInfo) GetAddress() []string {
246 + if x != nil {
247 + return x.Address
248 + }
249 + return nil
250 +}
251 +
252 +func (x *RelayInfo) GetLeases() []string {
253 + if x != nil {
254 + return x.Leases
255 + }
256 + return nil
257 +}
258 +
259 +type RelayInfoRequest struct {
260 + state protoimpl.MessageState `protogen:"open.v1"`
261 + unknownFields protoimpl.UnknownFields
262 + sizeCache protoimpl.SizeCache
263 +}
264 +
265 +func (x *RelayInfoRequest) Reset() {
266 + *x = RelayInfoRequest{}
267 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[2]
268 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
269 + ms.StoreMessageInfo(mi)
270 +}
271 +
272 +func (x *RelayInfoRequest) String() string {
273 + return protoimpl.X.MessageStringOf(x)
274 +}
275 +
276 +func (*RelayInfoRequest) ProtoMessage() {}
277 +
278 +func (x *RelayInfoRequest) ProtoReflect() protoreflect.Message {
279 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[2]
280 + if x != nil {
281 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
282 + if ms.LoadMessageInfo() == nil {
283 + ms.StoreMessageInfo(mi)
284 + }
285 + return ms
286 + }
287 + return mi.MessageOf(x)
288 +}
289 +
290 +// Deprecated: Use RelayInfoRequest.ProtoReflect.Descriptor instead.
291 +func (*RelayInfoRequest) Descriptor() ([]byte, []int) {
292 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{2}
293 +}
294 +
295 +type RelayInfoResponse struct {
296 + state protoimpl.MessageState `protogen:"open.v1"`
297 + RelayInfo *RelayInfo `protobuf:"bytes,1,opt,name=relay_info,json=relayInfo,proto3" json:"relay_info,omitempty"`
298 + unknownFields protoimpl.UnknownFields
299 + sizeCache protoimpl.SizeCache
300 +}
301 +
302 +func (x *RelayInfoResponse) Reset() {
303 + *x = RelayInfoResponse{}
304 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[3]
305 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
306 + ms.StoreMessageInfo(mi)
307 +}
308 +
309 +func (x *RelayInfoResponse) String() string {
310 + return protoimpl.X.MessageStringOf(x)
311 +}
312 +
313 +func (*RelayInfoResponse) ProtoMessage() {}
314 +
315 +func (x *RelayInfoResponse) ProtoReflect() protoreflect.Message {
316 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[3]
317 + if x != nil {
318 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
319 + if ms.LoadMessageInfo() == nil {
320 + ms.StoreMessageInfo(mi)
321 + }
322 + return ms
323 + }
324 + return mi.MessageOf(x)
325 +}
326 +
327 +// Deprecated: Use RelayInfoResponse.ProtoReflect.Descriptor instead.
328 +func (*RelayInfoResponse) Descriptor() ([]byte, []int) {
329 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{3}
330 +}
331 +
332 +func (x *RelayInfoResponse) GetRelayInfo() *RelayInfo {
333 + if x != nil {
334 + return x.RelayInfo
335 + }
336 + return nil
337 +}
338 +
339 +type Lease struct {
340 + state protoimpl.MessageState `protogen:"open.v1"`
341 + Identity *rdsec.Identity `protobuf:"bytes,1,opt,name=identity,proto3" json:"identity,omitempty"`
342 + Expires int64 `protobuf:"varint,2,opt,name=expires,proto3" json:"expires,omitempty"`
343 + Name string `protobuf:"bytes,3,opt,name=name,proto3" json:"name,omitempty"`
344 + Alpn []string `protobuf:"bytes,4,rep,name=alpn,proto3" json:"alpn,omitempty"`
345 + unknownFields protoimpl.UnknownFields
346 + sizeCache protoimpl.SizeCache
347 +}
348 +
349 +func (x *Lease) Reset() {
350 + *x = Lease{}
351 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[4]
352 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
353 + ms.StoreMessageInfo(mi)
354 +}
355 +
356 +func (x *Lease) String() string {
357 + return protoimpl.X.MessageStringOf(x)
358 +}
359 +
360 +func (*Lease) ProtoMessage() {}
361 +
362 +func (x *Lease) ProtoReflect() protoreflect.Message {
363 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[4]
364 + if x != nil {
365 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
366 + if ms.LoadMessageInfo() == nil {
367 + ms.StoreMessageInfo(mi)
368 + }
369 + return ms
370 + }
371 + return mi.MessageOf(x)
372 +}
373 +
374 +// Deprecated: Use Lease.ProtoReflect.Descriptor instead.
375 +func (*Lease) Descriptor() ([]byte, []int) {
376 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{4}
377 +}
378 +
379 +func (x *Lease) GetIdentity() *rdsec.Identity {
380 + if x != nil {
381 + return x.Identity
382 + }
383 + return nil
384 +}
385 +
386 +func (x *Lease) GetExpires() int64 {
387 + if x != nil {
388 + return x.Expires
389 + }
390 + return 0
391 +}
392 +
393 +func (x *Lease) GetName() string {
394 + if x != nil {
395 + return x.Name
396 + }
397 + return ""
398 +}
399 +
400 +func (x *Lease) GetAlpn() []string {
401 + if x != nil {
402 + return x.Alpn
403 + }
404 + return nil
405 +}
406 +
407 +type LeaseUpdateRequest struct {
408 + state protoimpl.MessageState `protogen:"open.v1"`
409 + Lease *Lease `protobuf:"bytes,1,opt,name=lease,proto3" json:"lease,omitempty"`
410 + Nonce []byte `protobuf:"bytes,2,opt,name=nonce,proto3" json:"nonce,omitempty"`
411 + Timestamp int64 `protobuf:"varint,3,opt,name=timestamp,proto3" json:"timestamp,omitempty"`
412 + unknownFields protoimpl.UnknownFields
413 + sizeCache protoimpl.SizeCache
414 +}
415 +
416 +func (x *LeaseUpdateRequest) Reset() {
417 + *x = LeaseUpdateRequest{}
418 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[5]
419 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
420 + ms.StoreMessageInfo(mi)
421 +}
422 +
423 +func (x *LeaseUpdateRequest) String() string {
424 + return protoimpl.X.MessageStringOf(x)
425 +}
426 +
427 +func (*LeaseUpdateRequest) ProtoMessage() {}
428 +
429 +func (x *LeaseUpdateRequest) ProtoReflect() protoreflect.Message {
430 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[5]
431 + if x != nil {
432 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
433 + if ms.LoadMessageInfo() == nil {
434 + ms.StoreMessageInfo(mi)
435 + }
436 + return ms
437 + }
438 + return mi.MessageOf(x)
439 +}
440 +
441 +// Deprecated: Use LeaseUpdateRequest.ProtoReflect.Descriptor instead.
442 +func (*LeaseUpdateRequest) Descriptor() ([]byte, []int) {
443 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{5}
444 +}
445 +
446 +func (x *LeaseUpdateRequest) GetLease() *Lease {
447 + if x != nil {
448 + return x.Lease
449 + }
450 + return nil
451 +}
452 +
453 +func (x *LeaseUpdateRequest) GetNonce() []byte {
454 + if x != nil {
455 + return x.Nonce
456 + }
457 + return nil
458 +}
459 +
460 +func (x *LeaseUpdateRequest) GetTimestamp() int64 {
461 + if x != nil {
462 + return x.Timestamp
463 + }
464 + return 0
465 +}
466 +
467 +type LeaseUpdateResponse struct {
468 + state protoimpl.MessageState `protogen:"open.v1"`
469 + Code ResponseCode `protobuf:"varint,1,opt,name=code,proto3,enum=rdverb.ResponseCode" json:"code,omitempty"`
470 + unknownFields protoimpl.UnknownFields
471 + sizeCache protoimpl.SizeCache
472 +}
473 +
474 +func (x *LeaseUpdateResponse) Reset() {
475 + *x = LeaseUpdateResponse{}
476 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[6]
477 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
478 + ms.StoreMessageInfo(mi)
479 +}
480 +
481 +func (x *LeaseUpdateResponse) String() string {
482 + return protoimpl.X.MessageStringOf(x)
483 +}
484 +
485 +func (*LeaseUpdateResponse) ProtoMessage() {}
486 +
487 +func (x *LeaseUpdateResponse) ProtoReflect() protoreflect.Message {
488 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[6]
489 + if x != nil {
490 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
491 + if ms.LoadMessageInfo() == nil {
492 + ms.StoreMessageInfo(mi)
493 + }
494 + return ms
495 + }
496 + return mi.MessageOf(x)
497 +}
498 +
499 +// Deprecated: Use LeaseUpdateResponse.ProtoReflect.Descriptor instead.
500 +func (*LeaseUpdateResponse) Descriptor() ([]byte, []int) {
501 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{6}
502 +}
503 +
504 +func (x *LeaseUpdateResponse) GetCode() ResponseCode {
505 + if x != nil {
506 + return x.Code
507 + }
508 + return ResponseCode_RESPONSE_CODE_ACCEPTED
509 +}
510 +
511 +type LeaseDeleteRequest struct {
512 + state protoimpl.MessageState `protogen:"open.v1"`
513 + Identity *rdsec.Identity `protobuf:"bytes,1,opt,name=identity,proto3" json:"identity,omitempty"`
514 + Nonce []byte `protobuf:"bytes,2,opt,name=nonce,proto3" json:"nonce,omitempty"`
515 + Timestamp int64 `protobuf:"varint,3,opt,name=timestamp,proto3" json:"timestamp,omitempty"`
516 + unknownFields protoimpl.UnknownFields
517 + sizeCache protoimpl.SizeCache
518 +}
519 +
520 +func (x *LeaseDeleteRequest) Reset() {
521 + *x = LeaseDeleteRequest{}
522 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[7]
523 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
524 + ms.StoreMessageInfo(mi)
525 +}
526 +
527 +func (x *LeaseDeleteRequest) String() string {
528 + return protoimpl.X.MessageStringOf(x)
529 +}
530 +
531 +func (*LeaseDeleteRequest) ProtoMessage() {}
532 +
533 +func (x *LeaseDeleteRequest) ProtoReflect() protoreflect.Message {
534 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[7]
535 + if x != nil {
536 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
537 + if ms.LoadMessageInfo() == nil {
538 + ms.StoreMessageInfo(mi)
539 + }
540 + return ms
541 + }
542 + return mi.MessageOf(x)
543 +}
544 +
545 +// Deprecated: Use LeaseDeleteRequest.ProtoReflect.Descriptor instead.
546 +func (*LeaseDeleteRequest) Descriptor() ([]byte, []int) {
547 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{7}
548 +}
549 +
550 +func (x *LeaseDeleteRequest) GetIdentity() *rdsec.Identity {
551 + if x != nil {
552 + return x.Identity
553 + }
554 + return nil
555 +}
556 +
557 +func (x *LeaseDeleteRequest) GetNonce() []byte {
558 + if x != nil {
559 + return x.Nonce
560 + }
561 + return nil
562 +}
563 +
564 +func (x *LeaseDeleteRequest) GetTimestamp() int64 {
565 + if x != nil {
566 + return x.Timestamp
567 + }
568 + return 0
569 +}
570 +
571 +type LeaseDeleteResponse struct {
572 + state protoimpl.MessageState `protogen:"open.v1"`
573 + Code ResponseCode `protobuf:"varint,1,opt,name=code,proto3,enum=rdverb.ResponseCode" json:"code,omitempty"`
574 + unknownFields protoimpl.UnknownFields
575 + sizeCache protoimpl.SizeCache
576 +}
577 +
578 +func (x *LeaseDeleteResponse) Reset() {
579 + *x = LeaseDeleteResponse{}
580 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[8]
581 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
582 + ms.StoreMessageInfo(mi)
583 +}
584 +
585 +func (x *LeaseDeleteResponse) String() string {
586 + return protoimpl.X.MessageStringOf(x)
587 +}
588 +
589 +func (*LeaseDeleteResponse) ProtoMessage() {}
590 +
591 +func (x *LeaseDeleteResponse) ProtoReflect() protoreflect.Message {
592 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[8]
593 + if x != nil {
594 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
595 + if ms.LoadMessageInfo() == nil {
596 + ms.StoreMessageInfo(mi)
597 + }
598 + return ms
599 + }
600 + return mi.MessageOf(x)
601 +}
602 +
603 +// Deprecated: Use LeaseDeleteResponse.ProtoReflect.Descriptor instead.
604 +func (*LeaseDeleteResponse) Descriptor() ([]byte, []int) {
605 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{8}
606 +}
607 +
608 +func (x *LeaseDeleteResponse) GetCode() ResponseCode {
609 + if x != nil {
610 + return x.Code
611 + }
612 + return ResponseCode_RESPONSE_CODE_ACCEPTED
613 +}
614 +
615 +type ConnectionRequest struct {
616 + state protoimpl.MessageState `protogen:"open.v1"`
617 + LeaseId string `protobuf:"bytes,1,opt,name=lease_id,json=leaseId,proto3" json:"lease_id,omitempty"`
618 + ClientIdentity *rdsec.Identity `protobuf:"bytes,2,opt,name=client_identity,json=clientIdentity,proto3" json:"client_identity,omitempty"`
619 + unknownFields protoimpl.UnknownFields
620 + sizeCache protoimpl.SizeCache
621 +}
622 +
623 +func (x *ConnectionRequest) Reset() {
624 + *x = ConnectionRequest{}
625 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[9]
626 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
627 + ms.StoreMessageInfo(mi)
628 +}
629 +
630 +func (x *ConnectionRequest) String() string {
631 + return protoimpl.X.MessageStringOf(x)
632 +}
633 +
634 +func (*ConnectionRequest) ProtoMessage() {}
635 +
636 +func (x *ConnectionRequest) ProtoReflect() protoreflect.Message {
637 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[9]
638 + if x != nil {
639 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
640 + if ms.LoadMessageInfo() == nil {
641 + ms.StoreMessageInfo(mi)
642 + }
643 + return ms
644 + }
645 + return mi.MessageOf(x)
646 +}
647 +
648 +// Deprecated: Use ConnectionRequest.ProtoReflect.Descriptor instead.
649 +func (*ConnectionRequest) Descriptor() ([]byte, []int) {
650 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{9}
651 +}
652 +
653 +func (x *ConnectionRequest) GetLeaseId() string {
654 + if x != nil {
655 + return x.LeaseId
656 + }
657 + return ""
658 +}
659 +
660 +func (x *ConnectionRequest) GetClientIdentity() *rdsec.Identity {
661 + if x != nil {
662 + return x.ClientIdentity
663 + }
664 + return nil
665 +}
666 +
667 +type ConnectionResponse struct {
668 + state protoimpl.MessageState `protogen:"open.v1"`
669 + Code ResponseCode `protobuf:"varint,1,opt,name=code,proto3,enum=rdverb.ResponseCode" json:"code,omitempty"`
670 + unknownFields protoimpl.UnknownFields
671 + sizeCache protoimpl.SizeCache
672 +}
673 +
674 +func (x *ConnectionResponse) Reset() {
675 + *x = ConnectionResponse{}
676 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[10]
677 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
678 + ms.StoreMessageInfo(mi)
679 +}
680 +
681 +func (x *ConnectionResponse) String() string {
682 + return protoimpl.X.MessageStringOf(x)
683 +}
684 +
685 +func (*ConnectionResponse) ProtoMessage() {}
686 +
687 +func (x *ConnectionResponse) ProtoReflect() protoreflect.Message {
688 + mi := &file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes[10]
689 + if x != nil {
690 + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
691 + if ms.LoadMessageInfo() == nil {
692 + ms.StoreMessageInfo(mi)
693 + }
694 + return ms
695 + }
696 + return mi.MessageOf(x)
697 +}
698 +
699 +// Deprecated: Use ConnectionResponse.ProtoReflect.Descriptor instead.
700 +func (*ConnectionResponse) Descriptor() ([]byte, []int) {
701 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP(), []int{10}
702 +}
703 +
704 +func (x *ConnectionResponse) GetCode() ResponseCode {
705 + if x != nil {
706 + return x.Code
707 + }
708 + return ResponseCode_RESPONSE_CODE_ACCEPTED
709 +}
710 +
711 +var File_relaydns_core_proto_rdverb_rdverb_proto protoreflect.FileDescriptor
712 +
713 +const file_relaydns_core_proto_rdverb_rdverb_proto_rawDesc = "" +
714 + "\n" +
715 + "'relaydns/core/proto/rdverb/rdverb.proto\x12\x06rdverb\x1a%relaydns/core/proto/rdsec/rdsec.proto\"J\n" +
716 + "\x06Packet\x12&\n" +
717 + "\x04type\x18\x01 \x01(\x0e2\x12.rdverb.PacketTypeR\x04type\x12\x18\n" +
718 + "\apayload\x18\x02 \x01(\fR\apayload\"j\n" +
719 + "\tRelayInfo\x12+\n" +
720 + "\bidentity\x18\x01 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x18\n" +
721 + "\aaddress\x18\x02 \x03(\tR\aaddress\x12\x16\n" +
722 + "\x06leases\x18\x03 \x03(\tR\x06leases\"\x12\n" +
723 + "\x10RelayInfoRequest\"E\n" +
724 + "\x11RelayInfoResponse\x120\n" +
725 + "\n" +
726 + "relay_info\x18\x01 \x01(\v2\x11.rdverb.RelayInfoR\trelayInfo\"v\n" +
727 + "\x05Lease\x12+\n" +
728 + "\bidentity\x18\x01 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x18\n" +
729 + "\aexpires\x18\x02 \x01(\x03R\aexpires\x12\x12\n" +
730 + "\x04name\x18\x03 \x01(\tR\x04name\x12\x12\n" +
731 + "\x04alpn\x18\x04 \x03(\tR\x04alpn\"m\n" +
732 + "\x12LeaseUpdateRequest\x12#\n" +
733 + "\x05lease\x18\x01 \x01(\v2\r.rdverb.LeaseR\x05lease\x12\x14\n" +
734 + "\x05nonce\x18\x02 \x01(\fR\x05nonce\x12\x1c\n" +
735 + "\ttimestamp\x18\x03 \x01(\x03R\ttimestamp\"?\n" +
736 + "\x13LeaseUpdateResponse\x12(\n" +
737 + "\x04code\x18\x01 \x01(\x0e2\x14.rdverb.ResponseCodeR\x04code\"u\n" +
738 + "\x12LeaseDeleteRequest\x12+\n" +
739 + "\bidentity\x18\x01 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x14\n" +
740 + "\x05nonce\x18\x02 \x01(\fR\x05nonce\x12\x1c\n" +
741 + "\ttimestamp\x18\x03 \x01(\x03R\ttimestamp\"?\n" +
742 + "\x13LeaseDeleteResponse\x12(\n" +
743 + "\x04code\x18\x01 \x01(\x0e2\x14.rdverb.ResponseCodeR\x04code\"h\n" +
744 + "\x11ConnectionRequest\x12\x19\n" +
745 + "\blease_id\x18\x01 \x01(\tR\aleaseId\x128\n" +
746 + "\x0fclient_identity\x18\x02 \x01(\v2\x0f.rdsec.IdentityR\x0eclientIdentity\">\n" +
747 + "\x12ConnectionResponse\x12(\n" +
748 + "\x04code\x18\x01 \x01(\x0e2\x14.rdverb.ResponseCodeR\x04code*\xb8\x02\n" +
749 + "\n" +
750 + "PacketType\x12\"\n" +
751 + "\x1ePACKET_TYPE_RELAY_INFO_REQUEST\x10\x00\x12#\n" +
752 + "\x1fPACKET_TYPE_RELAY_INFO_RESPONSE\x10\x01\x12$\n" +
753 + " PACKET_TYPE_LEASE_UPDATE_REQUEST\x10\x02\x12%\n" +
754 + "!PACKET_TYPE_LEASE_UPDATE_RESPONSE\x10\x03\x12$\n" +
755 + " PACKET_TYPE_LEASE_DELETE_REQUEST\x10\x04\x12%\n" +
756 + "!PACKET_TYPE_LEASE_DELETE_RESPONSE\x10\x05\x12\"\n" +
757 + "\x1ePACKET_TYPE_CONNECTION_REQUEST\x10\x06\x12#\n" +
758 + "\x1fPACKET_TYPE_CONNECTION_RESPONSE\x10\a*\xcd\x01\n" +
759 + "\fResponseCode\x12\x1a\n" +
760 + "\x16RESPONSE_CODE_ACCEPTED\x10\x00\x12!\n" +
761 + "\x1dRESPONSE_CODE_INVALID_EXPIRES\x10\x01\x12\"\n" +
762 + "\x1eRESPONSE_CODE_INVALID_IDENTITY\x10\x02\x12\x1e\n" +
763 + "\x1aRESPONSE_CODE_INVALID_NAME\x10\x03\x12\x1e\n" +
764 + "\x1aRESPONSE_CODE_INVALID_ALPN\x10\x04\x12\x1a\n" +
765 + "\x16RESPONSE_CODE_REJECTED\x10\x05B\x8f\x01\n" +
766 + "\n" +
767 + "com.rdverbB\vRdverbProtoP\x01Z<github.com/gosuda/relaydns/relaydns/core/proto/rdverb;rdverb\xa2\x02\x03RXX\xaa\x02\x06Rdverb\xca\x02\x06Rdverb\xe2\x02\x12Rdverb\\GPBMetadata\xea\x02\x06Rdverbb\x06proto3"
768 +
769 +var (
770 + file_relaydns_core_proto_rdverb_rdverb_proto_rawDescOnce sync.Once
771 + file_relaydns_core_proto_rdverb_rdverb_proto_rawDescData []byte
772 +)
773 +
774 +func file_relaydns_core_proto_rdverb_rdverb_proto_rawDescGZIP() []byte {
775 + file_relaydns_core_proto_rdverb_rdverb_proto_rawDescOnce.Do(func() {
776 + file_relaydns_core_proto_rdverb_rdverb_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_relaydns_core_proto_rdverb_rdverb_proto_rawDesc), len(file_relaydns_core_proto_rdverb_rdverb_proto_rawDesc)))
777 + })
778 + return file_relaydns_core_proto_rdverb_rdverb_proto_rawDescData
779 +}
780 +
781 +var file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes = make([]protoimpl.EnumInfo, 2)
782 +var file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes = make([]protoimpl.MessageInfo, 11)
783 +var file_relaydns_core_proto_rdverb_rdverb_proto_goTypes = []any{
784 + (PacketType)(0), // 0: rdverb.PacketType
785 + (ResponseCode)(0), // 1: rdverb.ResponseCode
786 + (*Packet)(nil), // 2: rdverb.Packet
787 + (*RelayInfo)(nil), // 3: rdverb.RelayInfo
788 + (*RelayInfoRequest)(nil), // 4: rdverb.RelayInfoRequest
789 + (*RelayInfoResponse)(nil), // 5: rdverb.RelayInfoResponse
790 + (*Lease)(nil), // 6: rdverb.Lease
791 + (*LeaseUpdateRequest)(nil), // 7: rdverb.LeaseUpdateRequest
792 + (*LeaseUpdateResponse)(nil), // 8: rdverb.LeaseUpdateResponse
793 + (*LeaseDeleteRequest)(nil), // 9: rdverb.LeaseDeleteRequest
794 + (*LeaseDeleteResponse)(nil), // 10: rdverb.LeaseDeleteResponse
795 + (*ConnectionRequest)(nil), // 11: rdverb.ConnectionRequest
796 + (*ConnectionResponse)(nil), // 12: rdverb.ConnectionResponse
797 + (*rdsec.Identity)(nil), // 13: rdsec.Identity
798 +}
799 +var file_relaydns_core_proto_rdverb_rdverb_proto_depIdxs = []int32{
800 + 0, // 0: rdverb.Packet.type:type_name -> rdverb.PacketType
801 + 13, // 1: rdverb.RelayInfo.identity:type_name -> rdsec.Identity
802 + 3, // 2: rdverb.RelayInfoResponse.relay_info:type_name -> rdverb.RelayInfo
803 + 13, // 3: rdverb.Lease.identity:type_name -> rdsec.Identity
804 + 6, // 4: rdverb.LeaseUpdateRequest.lease:type_name -> rdverb.Lease
805 + 1, // 5: rdverb.LeaseUpdateResponse.code:type_name -> rdverb.ResponseCode
806 + 13, // 6: rdverb.LeaseDeleteRequest.identity:type_name -> rdsec.Identity
807 + 1, // 7: rdverb.LeaseDeleteResponse.code:type_name -> rdverb.ResponseCode
808 + 13, // 8: rdverb.ConnectionRequest.client_identity:type_name -> rdsec.Identity
809 + 1, // 9: rdverb.ConnectionResponse.code:type_name -> rdverb.ResponseCode
810 + 10, // [10:10] is the sub-list for method output_type
811 + 10, // [10:10] is the sub-list for method input_type
812 + 10, // [10:10] is the sub-list for extension type_name
813 + 10, // [10:10] is the sub-list for extension extendee
814 + 0, // [0:10] is the sub-list for field type_name
815 +}
816 +
817 +func init() { file_relaydns_core_proto_rdverb_rdverb_proto_init() }
818 +func file_relaydns_core_proto_rdverb_rdverb_proto_init() {
819 + if File_relaydns_core_proto_rdverb_rdverb_proto != nil {
820 + return
821 + }
822 + type x struct{}
823 + out := protoimpl.TypeBuilder{
824 + File: protoimpl.DescBuilder{
825 + GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
826 + RawDescriptor: unsafe.Slice(unsafe.StringData(file_relaydns_core_proto_rdverb_rdverb_proto_rawDesc), len(file_relaydns_core_proto_rdverb_rdverb_proto_rawDesc)),
827 + NumEnums: 2,
828 + NumMessages: 11,
829 + NumExtensions: 0,
830 + NumServices: 0,
831 + },
832 + GoTypes: file_relaydns_core_proto_rdverb_rdverb_proto_goTypes,
833 + DependencyIndexes: file_relaydns_core_proto_rdverb_rdverb_proto_depIdxs,
834 + EnumInfos: file_relaydns_core_proto_rdverb_rdverb_proto_enumTypes,
835 + MessageInfos: file_relaydns_core_proto_rdverb_rdverb_proto_msgTypes,
836 + }.Build()
837 + File_relaydns_core_proto_rdverb_rdverb_proto = out.File
838 + file_relaydns_core_proto_rdverb_rdverb_proto_goTypes = nil
839 + file_relaydns_core_proto_rdverb_rdverb_proto_depIdxs = nil
840 +}
relaydns/core/proto/rdverb/rdverb.proto new
+85
@@ -0,0 +1,85 @@
1 +syntax = "proto3";
2 +
3 +package rdverb;
4 +
5 +import "relaydns/core/proto/rdsec/rdsec.proto";
6 +
7 +option go_package = "github.com/gosuda/relaydns/relaydns/core/proto/rdverb;rdverb";
8 +
9 +enum PacketType {
10 + PACKET_TYPE_RELAY_INFO_REQUEST = 0;
11 + PACKET_TYPE_RELAY_INFO_RESPONSE = 1;
12 +
13 + PACKET_TYPE_LEASE_UPDATE_REQUEST = 2; // Authenticated
14 + PACKET_TYPE_LEASE_UPDATE_RESPONSE = 3;
15 +
16 + PACKET_TYPE_LEASE_DELETE_REQUEST = 4; // Authenticated
17 + PACKET_TYPE_LEASE_DELETE_RESPONSE = 5;
18 +
19 + PACKET_TYPE_CONNECTION_REQUEST = 6;
20 + PACKET_TYPE_CONNECTION_RESPONSE = 7;
21 +}
22 +
23 +enum ResponseCode {
24 + RESPONSE_CODE_ACCEPTED = 0;
25 +
26 + RESPONSE_CODE_INVALID_EXPIRES = 1;
27 + RESPONSE_CODE_INVALID_IDENTITY = 2;
28 + RESPONSE_CODE_INVALID_NAME = 3;
29 + RESPONSE_CODE_INVALID_ALPN = 4;
30 +
31 + RESPONSE_CODE_REJECTED = 5;
32 +}
33 +
34 +message Packet {
35 + PacketType type = 1;
36 + bytes payload = 2;
37 +}
38 +
39 +message RelayInfo {
40 + rdsec.Identity identity = 1;
41 + repeated string address = 2;
42 + repeated string leases = 3;
43 +}
44 +
45 +message RelayInfoRequest {}
46 +
47 +message RelayInfoResponse {
48 + RelayInfo relay_info = 1;
49 +}
50 +
51 +message Lease {
52 + rdsec.Identity identity = 1;
53 + int64 expires = 2;
54 + string name = 3;
55 + repeated string alpn = 4;
56 +}
57 +
58 +message LeaseUpdateRequest {
59 + Lease lease = 1;
60 + bytes nonce = 2;
61 + int64 timestamp = 3;
62 +}
63 +
64 +message LeaseUpdateResponse {
65 + ResponseCode code = 1;
66 +}
67 +
68 +message LeaseDeleteRequest {
69 + rdsec.Identity identity = 1;
70 + bytes nonce = 2;
71 + int64 timestamp = 3;
72 +}
73 +
74 +message LeaseDeleteResponse {
75 + ResponseCode code = 1;
76 +}
77 +
78 +message ConnectionRequest {
79 + string lease_id = 1;
80 + rdsec.Identity client_identity = 2;
81 +}
82 +
83 +message ConnectionResponse {
84 + ResponseCode code = 1;
85 +}
relaydns/core/proto/rdverb/rdverb_vtproto.pb.go new
+4313
@@ -0,0 +1,4313 @@
1 +// Code generated by protoc-gen-go-vtproto. DO NOT EDIT.
2 +// protoc-gen-go-vtproto version: v0.6.0
3 +// source: relaydns/core/proto/rdverb/rdverb.proto
4 +
5 +package rdverb
6 +
7 +import (
8 + fmt "fmt"
9 + rdsec "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
10 + protohelpers "github.com/planetscale/vtprotobuf/protohelpers"
11 + proto "google.golang.org/protobuf/proto"
12 + protoimpl "google.golang.org/protobuf/runtime/protoimpl"
13 + io "io"
14 + unsafe "unsafe"
15 +)
16 +
17 +const (
18 + // Verify that this generated code is sufficiently up-to-date.
19 + _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
20 + // Verify that runtime/protoimpl is sufficiently up-to-date.
21 + _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
22 +)
23 +
24 +func (m *Packet) CloneVT() *Packet {
25 + if m == nil {
26 + return (*Packet)(nil)
27 + }
28 + r := new(Packet)
29 + r.Type = m.Type
30 + if rhs := m.Payload; rhs != nil {
31 + tmpBytes := make([]byte, len(rhs))
32 + copy(tmpBytes, rhs)
33 + r.Payload = tmpBytes
34 + }
35 + if len(m.unknownFields) > 0 {
36 + r.unknownFields = make([]byte, len(m.unknownFields))
37 + copy(r.unknownFields, m.unknownFields)
38 + }
39 + return r
40 +}
41 +
42 +func (m *Packet) CloneMessageVT() proto.Message {
43 + return m.CloneVT()
44 +}
45 +
46 +func (m *RelayInfo) CloneVT() *RelayInfo {
47 + if m == nil {
48 + return (*RelayInfo)(nil)
49 + }
50 + r := new(RelayInfo)
51 + if rhs := m.Identity; rhs != nil {
52 + if vtpb, ok := interface{}(rhs).(interface{ CloneVT() *rdsec.Identity }); ok {
53 + r.Identity = vtpb.CloneVT()
54 + } else {
55 + r.Identity = proto.Clone(rhs).(*rdsec.Identity)
56 + }
57 + }
58 + if rhs := m.Address; rhs != nil {
59 + tmpContainer := make([]string, len(rhs))
60 + copy(tmpContainer, rhs)
61 + r.Address = tmpContainer
62 + }
63 + if rhs := m.Leases; rhs != nil {
64 + tmpContainer := make([]string, len(rhs))
65 + copy(tmpContainer, rhs)
66 + r.Leases = tmpContainer
67 + }
68 + if len(m.unknownFields) > 0 {
69 + r.unknownFields = make([]byte, len(m.unknownFields))
70 + copy(r.unknownFields, m.unknownFields)
71 + }
72 + return r
73 +}
74 +
75 +func (m *RelayInfo) CloneMessageVT() proto.Message {
76 + return m.CloneVT()
77 +}
78 +
79 +func (m *RelayInfoRequest) CloneVT() *RelayInfoRequest {
80 + if m == nil {
81 + return (*RelayInfoRequest)(nil)
82 + }
83 + r := new(RelayInfoRequest)
84 + if len(m.unknownFields) > 0 {
85 + r.unknownFields = make([]byte, len(m.unknownFields))
86 + copy(r.unknownFields, m.unknownFields)
87 + }
88 + return r
89 +}
90 +
91 +func (m *RelayInfoRequest) CloneMessageVT() proto.Message {
92 + return m.CloneVT()
93 +}
94 +
95 +func (m *RelayInfoResponse) CloneVT() *RelayInfoResponse {
96 + if m == nil {
97 + return (*RelayInfoResponse)(nil)
98 + }
99 + r := new(RelayInfoResponse)
100 + r.RelayInfo = m.RelayInfo.CloneVT()
101 + if len(m.unknownFields) > 0 {
102 + r.unknownFields = make([]byte, len(m.unknownFields))
103 + copy(r.unknownFields, m.unknownFields)
104 + }
105 + return r
106 +}
107 +
108 +func (m *RelayInfoResponse) CloneMessageVT() proto.Message {
109 + return m.CloneVT()
110 +}
111 +
112 +func (m *Lease) CloneVT() *Lease {
113 + if m == nil {
114 + return (*Lease)(nil)
115 + }
116 + r := new(Lease)
117 + r.Expires = m.Expires
118 + r.Name = m.Name
119 + if rhs := m.Identity; rhs != nil {
120 + if vtpb, ok := interface{}(rhs).(interface{ CloneVT() *rdsec.Identity }); ok {
121 + r.Identity = vtpb.CloneVT()
122 + } else {
123 + r.Identity = proto.Clone(rhs).(*rdsec.Identity)
124 + }
125 + }
126 + if rhs := m.Alpn; rhs != nil {
127 + tmpContainer := make([]string, len(rhs))
128 + copy(tmpContainer, rhs)
129 + r.Alpn = tmpContainer
130 + }
131 + if len(m.unknownFields) > 0 {
132 + r.unknownFields = make([]byte, len(m.unknownFields))
133 + copy(r.unknownFields, m.unknownFields)
134 + }
135 + return r
136 +}
137 +
138 +func (m *Lease) CloneMessageVT() proto.Message {
139 + return m.CloneVT()
140 +}
141 +
142 +func (m *LeaseUpdateRequest) CloneVT() *LeaseUpdateRequest {
143 + if m == nil {
144 + return (*LeaseUpdateRequest)(nil)
145 + }
146 + r := new(LeaseUpdateRequest)
147 + r.Lease = m.Lease.CloneVT()
148 + r.Timestamp = m.Timestamp
149 + if rhs := m.Nonce; rhs != nil {
150 + tmpBytes := make([]byte, len(rhs))
151 + copy(tmpBytes, rhs)
152 + r.Nonce = tmpBytes
153 + }
154 + if len(m.unknownFields) > 0 {
155 + r.unknownFields = make([]byte, len(m.unknownFields))
156 + copy(r.unknownFields, m.unknownFields)
157 + }
158 + return r
159 +}
160 +
161 +func (m *LeaseUpdateRequest) CloneMessageVT() proto.Message {
162 + return m.CloneVT()
163 +}
164 +
165 +func (m *LeaseUpdateResponse) CloneVT() *LeaseUpdateResponse {
166 + if m == nil {
167 + return (*LeaseUpdateResponse)(nil)
168 + }
169 + r := new(LeaseUpdateResponse)
170 + r.Code = m.Code
171 + if len(m.unknownFields) > 0 {
172 + r.unknownFields = make([]byte, len(m.unknownFields))
173 + copy(r.unknownFields, m.unknownFields)
174 + }
175 + return r
176 +}
177 +
178 +func (m *LeaseUpdateResponse) CloneMessageVT() proto.Message {
179 + return m.CloneVT()
180 +}
181 +
182 +func (m *LeaseDeleteRequest) CloneVT() *LeaseDeleteRequest {
183 + if m == nil {
184 + return (*LeaseDeleteRequest)(nil)
185 + }
186 + r := new(LeaseDeleteRequest)
187 + r.Timestamp = m.Timestamp
188 + if rhs := m.Identity; rhs != nil {
189 + if vtpb, ok := interface{}(rhs).(interface{ CloneVT() *rdsec.Identity }); ok {
190 + r.Identity = vtpb.CloneVT()
191 + } else {
192 + r.Identity = proto.Clone(rhs).(*rdsec.Identity)
193 + }
194 + }
195 + if rhs := m.Nonce; rhs != nil {
196 + tmpBytes := make([]byte, len(rhs))
197 + copy(tmpBytes, rhs)
198 + r.Nonce = tmpBytes
199 + }
200 + if len(m.unknownFields) > 0 {
201 + r.unknownFields = make([]byte, len(m.unknownFields))
202 + copy(r.unknownFields, m.unknownFields)
203 + }
204 + return r
205 +}
206 +
207 +func (m *LeaseDeleteRequest) CloneMessageVT() proto.Message {
208 + return m.CloneVT()
209 +}
210 +
211 +func (m *LeaseDeleteResponse) CloneVT() *LeaseDeleteResponse {
212 + if m == nil {
213 + return (*LeaseDeleteResponse)(nil)
214 + }
215 + r := new(LeaseDeleteResponse)
216 + r.Code = m.Code
217 + if len(m.unknownFields) > 0 {
218 + r.unknownFields = make([]byte, len(m.unknownFields))
219 + copy(r.unknownFields, m.unknownFields)
220 + }
221 + return r
222 +}
223 +
224 +func (m *LeaseDeleteResponse) CloneMessageVT() proto.Message {
225 + return m.CloneVT()
226 +}
227 +
228 +func (m *ConnectionRequest) CloneVT() *ConnectionRequest {
229 + if m == nil {
230 + return (*ConnectionRequest)(nil)
231 + }
232 + r := new(ConnectionRequest)
233 + r.LeaseId = m.LeaseId
234 + if rhs := m.ClientIdentity; rhs != nil {
235 + if vtpb, ok := interface{}(rhs).(interface{ CloneVT() *rdsec.Identity }); ok {
236 + r.ClientIdentity = vtpb.CloneVT()
237 + } else {
238 + r.ClientIdentity = proto.Clone(rhs).(*rdsec.Identity)
239 + }
240 + }
241 + if len(m.unknownFields) > 0 {
242 + r.unknownFields = make([]byte, len(m.unknownFields))
243 + copy(r.unknownFields, m.unknownFields)
244 + }
245 + return r
246 +}
247 +
248 +func (m *ConnectionRequest) CloneMessageVT() proto.Message {
249 + return m.CloneVT()
250 +}
251 +
252 +func (m *ConnectionResponse) CloneVT() *ConnectionResponse {
253 + if m == nil {
254 + return (*ConnectionResponse)(nil)
255 + }
256 + r := new(ConnectionResponse)
257 + r.Code = m.Code
258 + if len(m.unknownFields) > 0 {
259 + r.unknownFields = make([]byte, len(m.unknownFields))
260 + copy(r.unknownFields, m.unknownFields)
261 + }
262 + return r
263 +}
264 +
265 +func (m *ConnectionResponse) CloneMessageVT() proto.Message {
266 + return m.CloneVT()
267 +}
268 +
269 +func (this *Packet) EqualVT(that *Packet) bool {
270 + if this == that {
271 + return true
272 + } else if this == nil || that == nil {
273 + return false
274 + }
275 + if this.Type != that.Type {
276 + return false
277 + }
278 + if string(this.Payload) != string(that.Payload) {
279 + return false
280 + }
281 + return string(this.unknownFields) == string(that.unknownFields)
282 +}
283 +
284 +func (this *Packet) EqualMessageVT(thatMsg proto.Message) bool {
285 + that, ok := thatMsg.(*Packet)
286 + if !ok {
287 + return false
288 + }
289 + return this.EqualVT(that)
290 +}
291 +func (this *RelayInfo) EqualVT(that *RelayInfo) bool {
292 + if this == that {
293 + return true
294 + } else if this == nil || that == nil {
295 + return false
296 + }
297 + if equal, ok := interface{}(this.Identity).(interface{ EqualVT(*rdsec.Identity) bool }); ok {
298 + if !equal.EqualVT(that.Identity) {
299 + return false
300 + }
301 + } else if !proto.Equal(this.Identity, that.Identity) {
302 + return false
303 + }
304 + if len(this.Address) != len(that.Address) {
305 + return false
306 + }
307 + for i, vx := range this.Address {
308 + vy := that.Address[i]
309 + if vx != vy {
310 + return false
311 + }
312 + }
313 + if len(this.Leases) != len(that.Leases) {
314 + return false
315 + }
316 + for i, vx := range this.Leases {
317 + vy := that.Leases[i]
318 + if vx != vy {
319 + return false
320 + }
321 + }
322 + return string(this.unknownFields) == string(that.unknownFields)
323 +}
324 +
325 +func (this *RelayInfo) EqualMessageVT(thatMsg proto.Message) bool {
326 + that, ok := thatMsg.(*RelayInfo)
327 + if !ok {
328 + return false
329 + }
330 + return this.EqualVT(that)
331 +}
332 +func (this *RelayInfoRequest) EqualVT(that *RelayInfoRequest) bool {
333 + if this == that {
334 + return true
335 + } else if this == nil || that == nil {
336 + return false
337 + }
338 + return string(this.unknownFields) == string(that.unknownFields)
339 +}
340 +
341 +func (this *RelayInfoRequest) EqualMessageVT(thatMsg proto.Message) bool {
342 + that, ok := thatMsg.(*RelayInfoRequest)
343 + if !ok {
344 + return false
345 + }
346 + return this.EqualVT(that)
347 +}
348 +func (this *RelayInfoResponse) EqualVT(that *RelayInfoResponse) bool {
349 + if this == that {
350 + return true
351 + } else if this == nil || that == nil {
352 + return false
353 + }
354 + if !this.RelayInfo.EqualVT(that.RelayInfo) {
355 + return false
356 + }
357 + return string(this.unknownFields) == string(that.unknownFields)
358 +}
359 +
360 +func (this *RelayInfoResponse) EqualMessageVT(thatMsg proto.Message) bool {
361 + that, ok := thatMsg.(*RelayInfoResponse)
362 + if !ok {
363 + return false
364 + }
365 + return this.EqualVT(that)
366 +}
367 +func (this *Lease) EqualVT(that *Lease) bool {
368 + if this == that {
369 + return true
370 + } else if this == nil || that == nil {
371 + return false
372 + }
373 + if equal, ok := interface{}(this.Identity).(interface{ EqualVT(*rdsec.Identity) bool }); ok {
374 + if !equal.EqualVT(that.Identity) {
375 + return false
376 + }
377 + } else if !proto.Equal(this.Identity, that.Identity) {
378 + return false
379 + }
380 + if this.Expires != that.Expires {
381 + return false
382 + }
383 + if this.Name != that.Name {
384 + return false
385 + }
386 + if len(this.Alpn) != len(that.Alpn) {
387 + return false
388 + }
389 + for i, vx := range this.Alpn {
390 + vy := that.Alpn[i]
391 + if vx != vy {
392 + return false
393 + }
394 + }
395 + return string(this.unknownFields) == string(that.unknownFields)
396 +}
397 +
398 +func (this *Lease) EqualMessageVT(thatMsg proto.Message) bool {
399 + that, ok := thatMsg.(*Lease)
400 + if !ok {
401 + return false
402 + }
403 + return this.EqualVT(that)
404 +}
405 +func (this *LeaseUpdateRequest) EqualVT(that *LeaseUpdateRequest) bool {
406 + if this == that {
407 + return true
408 + } else if this == nil || that == nil {
409 + return false
410 + }
411 + if !this.Lease.EqualVT(that.Lease) {
412 + return false
413 + }
414 + if string(this.Nonce) != string(that.Nonce) {
415 + return false
416 + }
417 + if this.Timestamp != that.Timestamp {
418 + return false
419 + }
420 + return string(this.unknownFields) == string(that.unknownFields)
421 +}
422 +
423 +func (this *LeaseUpdateRequest) EqualMessageVT(thatMsg proto.Message) bool {
424 + that, ok := thatMsg.(*LeaseUpdateRequest)
425 + if !ok {
426 + return false
427 + }
428 + return this.EqualVT(that)
429 +}
430 +func (this *LeaseUpdateResponse) EqualVT(that *LeaseUpdateResponse) bool {
431 + if this == that {
432 + return true
433 + } else if this == nil || that == nil {
434 + return false
435 + }
436 + if this.Code != that.Code {
437 + return false
438 + }
439 + return string(this.unknownFields) == string(that.unknownFields)
440 +}
441 +
442 +func (this *LeaseUpdateResponse) EqualMessageVT(thatMsg proto.Message) bool {
443 + that, ok := thatMsg.(*LeaseUpdateResponse)
444 + if !ok {
445 + return false
446 + }
447 + return this.EqualVT(that)
448 +}
449 +func (this *LeaseDeleteRequest) EqualVT(that *LeaseDeleteRequest) bool {
450 + if this == that {
451 + return true
452 + } else if this == nil || that == nil {
453 + return false
454 + }
455 + if equal, ok := interface{}(this.Identity).(interface{ EqualVT(*rdsec.Identity) bool }); ok {
456 + if !equal.EqualVT(that.Identity) {
457 + return false
458 + }
459 + } else if !proto.Equal(this.Identity, that.Identity) {
460 + return false
461 + }
462 + if string(this.Nonce) != string(that.Nonce) {
463 + return false
464 + }
465 + if this.Timestamp != that.Timestamp {
466 + return false
467 + }
468 + return string(this.unknownFields) == string(that.unknownFields)
469 +}
470 +
471 +func (this *LeaseDeleteRequest) EqualMessageVT(thatMsg proto.Message) bool {
472 + that, ok := thatMsg.(*LeaseDeleteRequest)
473 + if !ok {
474 + return false
475 + }
476 + return this.EqualVT(that)
477 +}
478 +func (this *LeaseDeleteResponse) EqualVT(that *LeaseDeleteResponse) bool {
479 + if this == that {
480 + return true
481 + } else if this == nil || that == nil {
482 + return false
483 + }
484 + if this.Code != that.Code {
485 + return false
486 + }
487 + return string(this.unknownFields) == string(that.unknownFields)
488 +}
489 +
490 +func (this *LeaseDeleteResponse) EqualMessageVT(thatMsg proto.Message) bool {
491 + that, ok := thatMsg.(*LeaseDeleteResponse)
492 + if !ok {
493 + return false
494 + }
495 + return this.EqualVT(that)
496 +}
497 +func (this *ConnectionRequest) EqualVT(that *ConnectionRequest) bool {
498 + if this == that {
499 + return true
500 + } else if this == nil || that == nil {
501 + return false
502 + }
503 + if this.LeaseId != that.LeaseId {
504 + return false
505 + }
506 + if equal, ok := interface{}(this.ClientIdentity).(interface{ EqualVT(*rdsec.Identity) bool }); ok {
507 + if !equal.EqualVT(that.ClientIdentity) {
508 + return false
509 + }
510 + } else if !proto.Equal(this.ClientIdentity, that.ClientIdentity) {
511 + return false
512 + }
513 + return string(this.unknownFields) == string(that.unknownFields)
514 +}
515 +
516 +func (this *ConnectionRequest) EqualMessageVT(thatMsg proto.Message) bool {
517 + that, ok := thatMsg.(*ConnectionRequest)
518 + if !ok {
519 + return false
520 + }
521 + return this.EqualVT(that)
522 +}
523 +func (this *ConnectionResponse) EqualVT(that *ConnectionResponse) bool {
524 + if this == that {
525 + return true
526 + } else if this == nil || that == nil {
527 + return false
528 + }
529 + if this.Code != that.Code {
530 + return false
531 + }
532 + return string(this.unknownFields) == string(that.unknownFields)
533 +}
534 +
535 +func (this *ConnectionResponse) EqualMessageVT(thatMsg proto.Message) bool {
536 + that, ok := thatMsg.(*ConnectionResponse)
537 + if !ok {
538 + return false
539 + }
540 + return this.EqualVT(that)
541 +}
542 +func (m *Packet) MarshalVT() (dAtA []byte, err error) {
543 + if m == nil {
544 + return nil, nil
545 + }
546 + size := m.SizeVT()
547 + dAtA = make([]byte, size)
548 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
549 + if err != nil {
550 + return nil, err
551 + }
552 + return dAtA[:n], nil
553 +}
554 +
555 +func (m *Packet) MarshalToVT(dAtA []byte) (int, error) {
556 + size := m.SizeVT()
557 + return m.MarshalToSizedBufferVT(dAtA[:size])
558 +}
559 +
560 +func (m *Packet) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
561 + if m == nil {
562 + return 0, nil
563 + }
564 + i := len(dAtA)
565 + _ = i
566 + var l int
567 + _ = l
568 + if m.unknownFields != nil {
569 + i -= len(m.unknownFields)
570 + copy(dAtA[i:], m.unknownFields)
571 + }
572 + if len(m.Payload) > 0 {
573 + i -= len(m.Payload)
574 + copy(dAtA[i:], m.Payload)
575 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Payload)))
576 + i--
577 + dAtA[i] = 0x12
578 + }
579 + if m.Type != 0 {
580 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Type))
581 + i--
582 + dAtA[i] = 0x8
583 + }
584 + return len(dAtA) - i, nil
585 +}
586 +
587 +func (m *RelayInfo) MarshalVT() (dAtA []byte, err error) {
588 + if m == nil {
589 + return nil, nil
590 + }
591 + size := m.SizeVT()
592 + dAtA = make([]byte, size)
593 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
594 + if err != nil {
595 + return nil, err
596 + }
597 + return dAtA[:n], nil
598 +}
599 +
600 +func (m *RelayInfo) MarshalToVT(dAtA []byte) (int, error) {
601 + size := m.SizeVT()
602 + return m.MarshalToSizedBufferVT(dAtA[:size])
603 +}
604 +
605 +func (m *RelayInfo) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
606 + if m == nil {
607 + return 0, nil
608 + }
609 + i := len(dAtA)
610 + _ = i
611 + var l int
612 + _ = l
613 + if m.unknownFields != nil {
614 + i -= len(m.unknownFields)
615 + copy(dAtA[i:], m.unknownFields)
616 + }
617 + if len(m.Leases) > 0 {
618 + for iNdEx := len(m.Leases) - 1; iNdEx >= 0; iNdEx-- {
619 + i -= len(m.Leases[iNdEx])
620 + copy(dAtA[i:], m.Leases[iNdEx])
621 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Leases[iNdEx])))
622 + i--
623 + dAtA[i] = 0x1a
624 + }
625 + }
626 + if len(m.Address) > 0 {
627 + for iNdEx := len(m.Address) - 1; iNdEx >= 0; iNdEx-- {
628 + i -= len(m.Address[iNdEx])
629 + copy(dAtA[i:], m.Address[iNdEx])
630 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Address[iNdEx])))
631 + i--
632 + dAtA[i] = 0x12
633 + }
634 + }
635 + if m.Identity != nil {
636 + if vtmsg, ok := interface{}(m.Identity).(interface {
637 + MarshalToSizedBufferVT([]byte) (int, error)
638 + }); ok {
639 + size, err := vtmsg.MarshalToSizedBufferVT(dAtA[:i])
640 + if err != nil {
641 + return 0, err
642 + }
643 + i -= size
644 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
645 + } else {
646 + encoded, err := proto.Marshal(m.Identity)
647 + if err != nil {
648 + return 0, err
649 + }
650 + i -= len(encoded)
651 + copy(dAtA[i:], encoded)
652 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
653 + }
654 + i--
655 + dAtA[i] = 0xa
656 + }
657 + return len(dAtA) - i, nil
658 +}
659 +
660 +func (m *RelayInfoRequest) MarshalVT() (dAtA []byte, err error) {
661 + if m == nil {
662 + return nil, nil
663 + }
664 + size := m.SizeVT()
665 + dAtA = make([]byte, size)
666 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
667 + if err != nil {
668 + return nil, err
669 + }
670 + return dAtA[:n], nil
671 +}
672 +
673 +func (m *RelayInfoRequest) MarshalToVT(dAtA []byte) (int, error) {
674 + size := m.SizeVT()
675 + return m.MarshalToSizedBufferVT(dAtA[:size])
676 +}
677 +
678 +func (m *RelayInfoRequest) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
679 + if m == nil {
680 + return 0, nil
681 + }
682 + i := len(dAtA)
683 + _ = i
684 + var l int
685 + _ = l
686 + if m.unknownFields != nil {
687 + i -= len(m.unknownFields)
688 + copy(dAtA[i:], m.unknownFields)
689 + }
690 + return len(dAtA) - i, nil
691 +}
692 +
693 +func (m *RelayInfoResponse) MarshalVT() (dAtA []byte, err error) {
694 + if m == nil {
695 + return nil, nil
696 + }
697 + size := m.SizeVT()
698 + dAtA = make([]byte, size)
699 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
700 + if err != nil {
701 + return nil, err
702 + }
703 + return dAtA[:n], nil
704 +}
705 +
706 +func (m *RelayInfoResponse) MarshalToVT(dAtA []byte) (int, error) {
707 + size := m.SizeVT()
708 + return m.MarshalToSizedBufferVT(dAtA[:size])
709 +}
710 +
711 +func (m *RelayInfoResponse) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
712 + if m == nil {
713 + return 0, nil
714 + }
715 + i := len(dAtA)
716 + _ = i
717 + var l int
718 + _ = l
719 + if m.unknownFields != nil {
720 + i -= len(m.unknownFields)
721 + copy(dAtA[i:], m.unknownFields)
722 + }
723 + if m.RelayInfo != nil {
724 + size, err := m.RelayInfo.MarshalToSizedBufferVT(dAtA[:i])
725 + if err != nil {
726 + return 0, err
727 + }
728 + i -= size
729 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
730 + i--
731 + dAtA[i] = 0xa
732 + }
733 + return len(dAtA) - i, nil
734 +}
735 +
736 +func (m *Lease) MarshalVT() (dAtA []byte, err error) {
737 + if m == nil {
738 + return nil, nil
739 + }
740 + size := m.SizeVT()
741 + dAtA = make([]byte, size)
742 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
743 + if err != nil {
744 + return nil, err
745 + }
746 + return dAtA[:n], nil
747 +}
748 +
749 +func (m *Lease) MarshalToVT(dAtA []byte) (int, error) {
750 + size := m.SizeVT()
751 + return m.MarshalToSizedBufferVT(dAtA[:size])
752 +}
753 +
754 +func (m *Lease) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
755 + if m == nil {
756 + return 0, nil
757 + }
758 + i := len(dAtA)
759 + _ = i
760 + var l int
761 + _ = l
762 + if m.unknownFields != nil {
763 + i -= len(m.unknownFields)
764 + copy(dAtA[i:], m.unknownFields)
765 + }
766 + if len(m.Alpn) > 0 {
767 + for iNdEx := len(m.Alpn) - 1; iNdEx >= 0; iNdEx-- {
768 + i -= len(m.Alpn[iNdEx])
769 + copy(dAtA[i:], m.Alpn[iNdEx])
770 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn[iNdEx])))
771 + i--
772 + dAtA[i] = 0x22
773 + }
774 + }
775 + if len(m.Name) > 0 {
776 + i -= len(m.Name)
777 + copy(dAtA[i:], m.Name)
778 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Name)))
779 + i--
780 + dAtA[i] = 0x1a
781 + }
782 + if m.Expires != 0 {
783 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Expires))
784 + i--
785 + dAtA[i] = 0x10
786 + }
787 + if m.Identity != nil {
788 + if vtmsg, ok := interface{}(m.Identity).(interface {
789 + MarshalToSizedBufferVT([]byte) (int, error)
790 + }); ok {
791 + size, err := vtmsg.MarshalToSizedBufferVT(dAtA[:i])
792 + if err != nil {
793 + return 0, err
794 + }
795 + i -= size
796 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
797 + } else {
798 + encoded, err := proto.Marshal(m.Identity)
799 + if err != nil {
800 + return 0, err
801 + }
802 + i -= len(encoded)
803 + copy(dAtA[i:], encoded)
804 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
805 + }
806 + i--
807 + dAtA[i] = 0xa
808 + }
809 + return len(dAtA) - i, nil
810 +}
811 +
812 +func (m *LeaseUpdateRequest) MarshalVT() (dAtA []byte, err error) {
813 + if m == nil {
814 + return nil, nil
815 + }
816 + size := m.SizeVT()
817 + dAtA = make([]byte, size)
818 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
819 + if err != nil {
820 + return nil, err
821 + }
822 + return dAtA[:n], nil
823 +}
824 +
825 +func (m *LeaseUpdateRequest) MarshalToVT(dAtA []byte) (int, error) {
826 + size := m.SizeVT()
827 + return m.MarshalToSizedBufferVT(dAtA[:size])
828 +}
829 +
830 +func (m *LeaseUpdateRequest) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
831 + if m == nil {
832 + return 0, nil
833 + }
834 + i := len(dAtA)
835 + _ = i
836 + var l int
837 + _ = l
838 + if m.unknownFields != nil {
839 + i -= len(m.unknownFields)
840 + copy(dAtA[i:], m.unknownFields)
841 + }
842 + if m.Timestamp != 0 {
843 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
844 + i--
845 + dAtA[i] = 0x18
846 + }
847 + if len(m.Nonce) > 0 {
848 + i -= len(m.Nonce)
849 + copy(dAtA[i:], m.Nonce)
850 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
851 + i--
852 + dAtA[i] = 0x12
853 + }
854 + if m.Lease != nil {
855 + size, err := m.Lease.MarshalToSizedBufferVT(dAtA[:i])
856 + if err != nil {
857 + return 0, err
858 + }
859 + i -= size
860 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
861 + i--
862 + dAtA[i] = 0xa
863 + }
864 + return len(dAtA) - i, nil
865 +}
866 +
867 +func (m *LeaseUpdateResponse) MarshalVT() (dAtA []byte, err error) {
868 + if m == nil {
869 + return nil, nil
870 + }
871 + size := m.SizeVT()
872 + dAtA = make([]byte, size)
873 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
874 + if err != nil {
875 + return nil, err
876 + }
877 + return dAtA[:n], nil
878 +}
879 +
880 +func (m *LeaseUpdateResponse) MarshalToVT(dAtA []byte) (int, error) {
881 + size := m.SizeVT()
882 + return m.MarshalToSizedBufferVT(dAtA[:size])
883 +}
884 +
885 +func (m *LeaseUpdateResponse) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
886 + if m == nil {
887 + return 0, nil
888 + }
889 + i := len(dAtA)
890 + _ = i
891 + var l int
892 + _ = l
893 + if m.unknownFields != nil {
894 + i -= len(m.unknownFields)
895 + copy(dAtA[i:], m.unknownFields)
896 + }
897 + if m.Code != 0 {
898 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
899 + i--
900 + dAtA[i] = 0x8
901 + }
902 + return len(dAtA) - i, nil
903 +}
904 +
905 +func (m *LeaseDeleteRequest) MarshalVT() (dAtA []byte, err error) {
906 + if m == nil {
907 + return nil, nil
908 + }
909 + size := m.SizeVT()
910 + dAtA = make([]byte, size)
911 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
912 + if err != nil {
913 + return nil, err
914 + }
915 + return dAtA[:n], nil
916 +}
917 +
918 +func (m *LeaseDeleteRequest) MarshalToVT(dAtA []byte) (int, error) {
919 + size := m.SizeVT()
920 + return m.MarshalToSizedBufferVT(dAtA[:size])
921 +}
922 +
923 +func (m *LeaseDeleteRequest) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
924 + if m == nil {
925 + return 0, nil
926 + }
927 + i := len(dAtA)
928 + _ = i
929 + var l int
930 + _ = l
931 + if m.unknownFields != nil {
932 + i -= len(m.unknownFields)
933 + copy(dAtA[i:], m.unknownFields)
934 + }
935 + if m.Timestamp != 0 {
936 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
937 + i--
938 + dAtA[i] = 0x18
939 + }
940 + if len(m.Nonce) > 0 {
941 + i -= len(m.Nonce)
942 + copy(dAtA[i:], m.Nonce)
943 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
944 + i--
945 + dAtA[i] = 0x12
946 + }
947 + if m.Identity != nil {
948 + if vtmsg, ok := interface{}(m.Identity).(interface {
949 + MarshalToSizedBufferVT([]byte) (int, error)
950 + }); ok {
951 + size, err := vtmsg.MarshalToSizedBufferVT(dAtA[:i])
952 + if err != nil {
953 + return 0, err
954 + }
955 + i -= size
956 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
957 + } else {
958 + encoded, err := proto.Marshal(m.Identity)
959 + if err != nil {
960 + return 0, err
961 + }
962 + i -= len(encoded)
963 + copy(dAtA[i:], encoded)
964 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
965 + }
966 + i--
967 + dAtA[i] = 0xa
968 + }
969 + return len(dAtA) - i, nil
970 +}
971 +
972 +func (m *LeaseDeleteResponse) MarshalVT() (dAtA []byte, err error) {
973 + if m == nil {
974 + return nil, nil
975 + }
976 + size := m.SizeVT()
977 + dAtA = make([]byte, size)
978 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
979 + if err != nil {
980 + return nil, err
981 + }
982 + return dAtA[:n], nil
983 +}
984 +
985 +func (m *LeaseDeleteResponse) MarshalToVT(dAtA []byte) (int, error) {
986 + size := m.SizeVT()
987 + return m.MarshalToSizedBufferVT(dAtA[:size])
988 +}
989 +
990 +func (m *LeaseDeleteResponse) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
991 + if m == nil {
992 + return 0, nil
993 + }
994 + i := len(dAtA)
995 + _ = i
996 + var l int
997 + _ = l
998 + if m.unknownFields != nil {
999 + i -= len(m.unknownFields)
1000 + copy(dAtA[i:], m.unknownFields)
1001 + }
1002 + if m.Code != 0 {
1003 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
1004 + i--
1005 + dAtA[i] = 0x8
1006 + }
1007 + return len(dAtA) - i, nil
1008 +}
1009 +
1010 +func (m *ConnectionRequest) MarshalVT() (dAtA []byte, err error) {
1011 + if m == nil {
1012 + return nil, nil
1013 + }
1014 + size := m.SizeVT()
1015 + dAtA = make([]byte, size)
1016 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
1017 + if err != nil {
1018 + return nil, err
1019 + }
1020 + return dAtA[:n], nil
1021 +}
1022 +
1023 +func (m *ConnectionRequest) MarshalToVT(dAtA []byte) (int, error) {
1024 + size := m.SizeVT()
1025 + return m.MarshalToSizedBufferVT(dAtA[:size])
1026 +}
1027 +
1028 +func (m *ConnectionRequest) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
1029 + if m == nil {
1030 + return 0, nil
1031 + }
1032 + i := len(dAtA)
1033 + _ = i
1034 + var l int
1035 + _ = l
1036 + if m.unknownFields != nil {
1037 + i -= len(m.unknownFields)
1038 + copy(dAtA[i:], m.unknownFields)
1039 + }
1040 + if m.ClientIdentity != nil {
1041 + if vtmsg, ok := interface{}(m.ClientIdentity).(interface {
1042 + MarshalToSizedBufferVT([]byte) (int, error)
1043 + }); ok {
1044 + size, err := vtmsg.MarshalToSizedBufferVT(dAtA[:i])
1045 + if err != nil {
1046 + return 0, err
1047 + }
1048 + i -= size
1049 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1050 + } else {
1051 + encoded, err := proto.Marshal(m.ClientIdentity)
1052 + if err != nil {
1053 + return 0, err
1054 + }
1055 + i -= len(encoded)
1056 + copy(dAtA[i:], encoded)
1057 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
1058 + }
1059 + i--
1060 + dAtA[i] = 0x12
1061 + }
1062 + if len(m.LeaseId) > 0 {
1063 + i -= len(m.LeaseId)
1064 + copy(dAtA[i:], m.LeaseId)
1065 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.LeaseId)))
1066 + i--
1067 + dAtA[i] = 0xa
1068 + }
1069 + return len(dAtA) - i, nil
1070 +}
1071 +
1072 +func (m *ConnectionResponse) MarshalVT() (dAtA []byte, err error) {
1073 + if m == nil {
1074 + return nil, nil
1075 + }
1076 + size := m.SizeVT()
1077 + dAtA = make([]byte, size)
1078 + n, err := m.MarshalToSizedBufferVT(dAtA[:size])
1079 + if err != nil {
1080 + return nil, err
1081 + }
1082 + return dAtA[:n], nil
1083 +}
1084 +
1085 +func (m *ConnectionResponse) MarshalToVT(dAtA []byte) (int, error) {
1086 + size := m.SizeVT()
1087 + return m.MarshalToSizedBufferVT(dAtA[:size])
1088 +}
1089 +
1090 +func (m *ConnectionResponse) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
1091 + if m == nil {
1092 + return 0, nil
1093 + }
1094 + i := len(dAtA)
1095 + _ = i
1096 + var l int
1097 + _ = l
1098 + if m.unknownFields != nil {
1099 + i -= len(m.unknownFields)
1100 + copy(dAtA[i:], m.unknownFields)
1101 + }
1102 + if m.Code != 0 {
1103 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
1104 + i--
1105 + dAtA[i] = 0x8
1106 + }
1107 + return len(dAtA) - i, nil
1108 +}
1109 +
1110 +func (m *Packet) MarshalVTStrict() (dAtA []byte, err error) {
1111 + if m == nil {
1112 + return nil, nil
1113 + }
1114 + size := m.SizeVT()
1115 + dAtA = make([]byte, size)
1116 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1117 + if err != nil {
1118 + return nil, err
1119 + }
1120 + return dAtA[:n], nil
1121 +}
1122 +
1123 +func (m *Packet) MarshalToVTStrict(dAtA []byte) (int, error) {
1124 + size := m.SizeVT()
1125 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1126 +}
1127 +
1128 +func (m *Packet) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1129 + if m == nil {
1130 + return 0, nil
1131 + }
1132 + i := len(dAtA)
1133 + _ = i
1134 + var l int
1135 + _ = l
1136 + if m.unknownFields != nil {
1137 + i -= len(m.unknownFields)
1138 + copy(dAtA[i:], m.unknownFields)
1139 + }
1140 + if len(m.Payload) > 0 {
1141 + i -= len(m.Payload)
1142 + copy(dAtA[i:], m.Payload)
1143 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Payload)))
1144 + i--
1145 + dAtA[i] = 0x12
1146 + }
1147 + if m.Type != 0 {
1148 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Type))
1149 + i--
1150 + dAtA[i] = 0x8
1151 + }
1152 + return len(dAtA) - i, nil
1153 +}
1154 +
1155 +func (m *RelayInfo) MarshalVTStrict() (dAtA []byte, err error) {
1156 + if m == nil {
1157 + return nil, nil
1158 + }
1159 + size := m.SizeVT()
1160 + dAtA = make([]byte, size)
1161 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1162 + if err != nil {
1163 + return nil, err
1164 + }
1165 + return dAtA[:n], nil
1166 +}
1167 +
1168 +func (m *RelayInfo) MarshalToVTStrict(dAtA []byte) (int, error) {
1169 + size := m.SizeVT()
1170 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1171 +}
1172 +
1173 +func (m *RelayInfo) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1174 + if m == nil {
1175 + return 0, nil
1176 + }
1177 + i := len(dAtA)
1178 + _ = i
1179 + var l int
1180 + _ = l
1181 + if m.unknownFields != nil {
1182 + i -= len(m.unknownFields)
1183 + copy(dAtA[i:], m.unknownFields)
1184 + }
1185 + if len(m.Leases) > 0 {
1186 + for iNdEx := len(m.Leases) - 1; iNdEx >= 0; iNdEx-- {
1187 + i -= len(m.Leases[iNdEx])
1188 + copy(dAtA[i:], m.Leases[iNdEx])
1189 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Leases[iNdEx])))
1190 + i--
1191 + dAtA[i] = 0x1a
1192 + }
1193 + }
1194 + if len(m.Address) > 0 {
1195 + for iNdEx := len(m.Address) - 1; iNdEx >= 0; iNdEx-- {
1196 + i -= len(m.Address[iNdEx])
1197 + copy(dAtA[i:], m.Address[iNdEx])
1198 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Address[iNdEx])))
1199 + i--
1200 + dAtA[i] = 0x12
1201 + }
1202 + }
1203 + if m.Identity != nil {
1204 + if vtmsg, ok := interface{}(m.Identity).(interface {
1205 + MarshalToSizedBufferVTStrict([]byte) (int, error)
1206 + }); ok {
1207 + size, err := vtmsg.MarshalToSizedBufferVTStrict(dAtA[:i])
1208 + if err != nil {
1209 + return 0, err
1210 + }
1211 + i -= size
1212 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1213 + } else {
1214 + encoded, err := proto.Marshal(m.Identity)
1215 + if err != nil {
1216 + return 0, err
1217 + }
1218 + i -= len(encoded)
1219 + copy(dAtA[i:], encoded)
1220 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
1221 + }
1222 + i--
1223 + dAtA[i] = 0xa
1224 + }
1225 + return len(dAtA) - i, nil
1226 +}
1227 +
1228 +func (m *RelayInfoRequest) MarshalVTStrict() (dAtA []byte, err error) {
1229 + if m == nil {
1230 + return nil, nil
1231 + }
1232 + size := m.SizeVT()
1233 + dAtA = make([]byte, size)
1234 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1235 + if err != nil {
1236 + return nil, err
1237 + }
1238 + return dAtA[:n], nil
1239 +}
1240 +
1241 +func (m *RelayInfoRequest) MarshalToVTStrict(dAtA []byte) (int, error) {
1242 + size := m.SizeVT()
1243 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1244 +}
1245 +
1246 +func (m *RelayInfoRequest) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1247 + if m == nil {
1248 + return 0, nil
1249 + }
1250 + i := len(dAtA)
1251 + _ = i
1252 + var l int
1253 + _ = l
1254 + if m.unknownFields != nil {
1255 + i -= len(m.unknownFields)
1256 + copy(dAtA[i:], m.unknownFields)
1257 + }
1258 + return len(dAtA) - i, nil
1259 +}
1260 +
1261 +func (m *RelayInfoResponse) MarshalVTStrict() (dAtA []byte, err error) {
1262 + if m == nil {
1263 + return nil, nil
1264 + }
1265 + size := m.SizeVT()
1266 + dAtA = make([]byte, size)
1267 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1268 + if err != nil {
1269 + return nil, err
1270 + }
1271 + return dAtA[:n], nil
1272 +}
1273 +
1274 +func (m *RelayInfoResponse) MarshalToVTStrict(dAtA []byte) (int, error) {
1275 + size := m.SizeVT()
1276 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1277 +}
1278 +
1279 +func (m *RelayInfoResponse) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1280 + if m == nil {
1281 + return 0, nil
1282 + }
1283 + i := len(dAtA)
1284 + _ = i
1285 + var l int
1286 + _ = l
1287 + if m.unknownFields != nil {
1288 + i -= len(m.unknownFields)
1289 + copy(dAtA[i:], m.unknownFields)
1290 + }
1291 + if m.RelayInfo != nil {
1292 + size, err := m.RelayInfo.MarshalToSizedBufferVTStrict(dAtA[:i])
1293 + if err != nil {
1294 + return 0, err
1295 + }
1296 + i -= size
1297 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1298 + i--
1299 + dAtA[i] = 0xa
1300 + }
1301 + return len(dAtA) - i, nil
1302 +}
1303 +
1304 +func (m *Lease) MarshalVTStrict() (dAtA []byte, err error) {
1305 + if m == nil {
1306 + return nil, nil
1307 + }
1308 + size := m.SizeVT()
1309 + dAtA = make([]byte, size)
1310 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1311 + if err != nil {
1312 + return nil, err
1313 + }
1314 + return dAtA[:n], nil
1315 +}
1316 +
1317 +func (m *Lease) MarshalToVTStrict(dAtA []byte) (int, error) {
1318 + size := m.SizeVT()
1319 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1320 +}
1321 +
1322 +func (m *Lease) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1323 + if m == nil {
1324 + return 0, nil
1325 + }
1326 + i := len(dAtA)
1327 + _ = i
1328 + var l int
1329 + _ = l
1330 + if m.unknownFields != nil {
1331 + i -= len(m.unknownFields)
1332 + copy(dAtA[i:], m.unknownFields)
1333 + }
1334 + if len(m.Alpn) > 0 {
1335 + for iNdEx := len(m.Alpn) - 1; iNdEx >= 0; iNdEx-- {
1336 + i -= len(m.Alpn[iNdEx])
1337 + copy(dAtA[i:], m.Alpn[iNdEx])
1338 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Alpn[iNdEx])))
1339 + i--
1340 + dAtA[i] = 0x22
1341 + }
1342 + }
1343 + if len(m.Name) > 0 {
1344 + i -= len(m.Name)
1345 + copy(dAtA[i:], m.Name)
1346 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Name)))
1347 + i--
1348 + dAtA[i] = 0x1a
1349 + }
1350 + if m.Expires != 0 {
1351 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Expires))
1352 + i--
1353 + dAtA[i] = 0x10
1354 + }
1355 + if m.Identity != nil {
1356 + if vtmsg, ok := interface{}(m.Identity).(interface {
1357 + MarshalToSizedBufferVTStrict([]byte) (int, error)
1358 + }); ok {
1359 + size, err := vtmsg.MarshalToSizedBufferVTStrict(dAtA[:i])
1360 + if err != nil {
1361 + return 0, err
1362 + }
1363 + i -= size
1364 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1365 + } else {
1366 + encoded, err := proto.Marshal(m.Identity)
1367 + if err != nil {
1368 + return 0, err
1369 + }
1370 + i -= len(encoded)
1371 + copy(dAtA[i:], encoded)
1372 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
1373 + }
1374 + i--
1375 + dAtA[i] = 0xa
1376 + }
1377 + return len(dAtA) - i, nil
1378 +}
1379 +
1380 +func (m *LeaseUpdateRequest) MarshalVTStrict() (dAtA []byte, err error) {
1381 + if m == nil {
1382 + return nil, nil
1383 + }
1384 + size := m.SizeVT()
1385 + dAtA = make([]byte, size)
1386 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1387 + if err != nil {
1388 + return nil, err
1389 + }
1390 + return dAtA[:n], nil
1391 +}
1392 +
1393 +func (m *LeaseUpdateRequest) MarshalToVTStrict(dAtA []byte) (int, error) {
1394 + size := m.SizeVT()
1395 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1396 +}
1397 +
1398 +func (m *LeaseUpdateRequest) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1399 + if m == nil {
1400 + return 0, nil
1401 + }
1402 + i := len(dAtA)
1403 + _ = i
1404 + var l int
1405 + _ = l
1406 + if m.unknownFields != nil {
1407 + i -= len(m.unknownFields)
1408 + copy(dAtA[i:], m.unknownFields)
1409 + }
1410 + if m.Timestamp != 0 {
1411 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
1412 + i--
1413 + dAtA[i] = 0x18
1414 + }
1415 + if len(m.Nonce) > 0 {
1416 + i -= len(m.Nonce)
1417 + copy(dAtA[i:], m.Nonce)
1418 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
1419 + i--
1420 + dAtA[i] = 0x12
1421 + }
1422 + if m.Lease != nil {
1423 + size, err := m.Lease.MarshalToSizedBufferVTStrict(dAtA[:i])
1424 + if err != nil {
1425 + return 0, err
1426 + }
1427 + i -= size
1428 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1429 + i--
1430 + dAtA[i] = 0xa
1431 + }
1432 + return len(dAtA) - i, nil
1433 +}
1434 +
1435 +func (m *LeaseUpdateResponse) MarshalVTStrict() (dAtA []byte, err error) {
1436 + if m == nil {
1437 + return nil, nil
1438 + }
1439 + size := m.SizeVT()
1440 + dAtA = make([]byte, size)
1441 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1442 + if err != nil {
1443 + return nil, err
1444 + }
1445 + return dAtA[:n], nil
1446 +}
1447 +
1448 +func (m *LeaseUpdateResponse) MarshalToVTStrict(dAtA []byte) (int, error) {
1449 + size := m.SizeVT()
1450 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1451 +}
1452 +
1453 +func (m *LeaseUpdateResponse) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1454 + if m == nil {
1455 + return 0, nil
1456 + }
1457 + i := len(dAtA)
1458 + _ = i
1459 + var l int
1460 + _ = l
1461 + if m.unknownFields != nil {
1462 + i -= len(m.unknownFields)
1463 + copy(dAtA[i:], m.unknownFields)
1464 + }
1465 + if m.Code != 0 {
1466 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
1467 + i--
1468 + dAtA[i] = 0x8
1469 + }
1470 + return len(dAtA) - i, nil
1471 +}
1472 +
1473 +func (m *LeaseDeleteRequest) MarshalVTStrict() (dAtA []byte, err error) {
1474 + if m == nil {
1475 + return nil, nil
1476 + }
1477 + size := m.SizeVT()
1478 + dAtA = make([]byte, size)
1479 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1480 + if err != nil {
1481 + return nil, err
1482 + }
1483 + return dAtA[:n], nil
1484 +}
1485 +
1486 +func (m *LeaseDeleteRequest) MarshalToVTStrict(dAtA []byte) (int, error) {
1487 + size := m.SizeVT()
1488 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1489 +}
1490 +
1491 +func (m *LeaseDeleteRequest) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1492 + if m == nil {
1493 + return 0, nil
1494 + }
1495 + i := len(dAtA)
1496 + _ = i
1497 + var l int
1498 + _ = l
1499 + if m.unknownFields != nil {
1500 + i -= len(m.unknownFields)
1501 + copy(dAtA[i:], m.unknownFields)
1502 + }
1503 + if m.Timestamp != 0 {
1504 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Timestamp))
1505 + i--
1506 + dAtA[i] = 0x18
1507 + }
1508 + if len(m.Nonce) > 0 {
1509 + i -= len(m.Nonce)
1510 + copy(dAtA[i:], m.Nonce)
1511 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Nonce)))
1512 + i--
1513 + dAtA[i] = 0x12
1514 + }
1515 + if m.Identity != nil {
1516 + if vtmsg, ok := interface{}(m.Identity).(interface {
1517 + MarshalToSizedBufferVTStrict([]byte) (int, error)
1518 + }); ok {
1519 + size, err := vtmsg.MarshalToSizedBufferVTStrict(dAtA[:i])
1520 + if err != nil {
1521 + return 0, err
1522 + }
1523 + i -= size
1524 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1525 + } else {
1526 + encoded, err := proto.Marshal(m.Identity)
1527 + if err != nil {
1528 + return 0, err
1529 + }
1530 + i -= len(encoded)
1531 + copy(dAtA[i:], encoded)
1532 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
1533 + }
1534 + i--
1535 + dAtA[i] = 0xa
1536 + }
1537 + return len(dAtA) - i, nil
1538 +}
1539 +
1540 +func (m *LeaseDeleteResponse) MarshalVTStrict() (dAtA []byte, err error) {
1541 + if m == nil {
1542 + return nil, nil
1543 + }
1544 + size := m.SizeVT()
1545 + dAtA = make([]byte, size)
1546 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1547 + if err != nil {
1548 + return nil, err
1549 + }
1550 + return dAtA[:n], nil
1551 +}
1552 +
1553 +func (m *LeaseDeleteResponse) MarshalToVTStrict(dAtA []byte) (int, error) {
1554 + size := m.SizeVT()
1555 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1556 +}
1557 +
1558 +func (m *LeaseDeleteResponse) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1559 + if m == nil {
1560 + return 0, nil
1561 + }
1562 + i := len(dAtA)
1563 + _ = i
1564 + var l int
1565 + _ = l
1566 + if m.unknownFields != nil {
1567 + i -= len(m.unknownFields)
1568 + copy(dAtA[i:], m.unknownFields)
1569 + }
1570 + if m.Code != 0 {
1571 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
1572 + i--
1573 + dAtA[i] = 0x8
1574 + }
1575 + return len(dAtA) - i, nil
1576 +}
1577 +
1578 +func (m *ConnectionRequest) MarshalVTStrict() (dAtA []byte, err error) {
1579 + if m == nil {
1580 + return nil, nil
1581 + }
1582 + size := m.SizeVT()
1583 + dAtA = make([]byte, size)
1584 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1585 + if err != nil {
1586 + return nil, err
1587 + }
1588 + return dAtA[:n], nil
1589 +}
1590 +
1591 +func (m *ConnectionRequest) MarshalToVTStrict(dAtA []byte) (int, error) {
1592 + size := m.SizeVT()
1593 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1594 +}
1595 +
1596 +func (m *ConnectionRequest) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1597 + if m == nil {
1598 + return 0, nil
1599 + }
1600 + i := len(dAtA)
1601 + _ = i
1602 + var l int
1603 + _ = l
1604 + if m.unknownFields != nil {
1605 + i -= len(m.unknownFields)
1606 + copy(dAtA[i:], m.unknownFields)
1607 + }
1608 + if m.ClientIdentity != nil {
1609 + if vtmsg, ok := interface{}(m.ClientIdentity).(interface {
1610 + MarshalToSizedBufferVTStrict([]byte) (int, error)
1611 + }); ok {
1612 + size, err := vtmsg.MarshalToSizedBufferVTStrict(dAtA[:i])
1613 + if err != nil {
1614 + return 0, err
1615 + }
1616 + i -= size
1617 + i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1618 + } else {
1619 + encoded, err := proto.Marshal(m.ClientIdentity)
1620 + if err != nil {
1621 + return 0, err
1622 + }
1623 + i -= len(encoded)
1624 + copy(dAtA[i:], encoded)
1625 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(encoded)))
1626 + }
1627 + i--
1628 + dAtA[i] = 0x12
1629 + }
1630 + if len(m.LeaseId) > 0 {
1631 + i -= len(m.LeaseId)
1632 + copy(dAtA[i:], m.LeaseId)
1633 + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.LeaseId)))
1634 + i--
1635 + dAtA[i] = 0xa
1636 + }
1637 + return len(dAtA) - i, nil
1638 +}
1639 +
1640 +func (m *ConnectionResponse) MarshalVTStrict() (dAtA []byte, err error) {
1641 + if m == nil {
1642 + return nil, nil
1643 + }
1644 + size := m.SizeVT()
1645 + dAtA = make([]byte, size)
1646 + n, err := m.MarshalToSizedBufferVTStrict(dAtA[:size])
1647 + if err != nil {
1648 + return nil, err
1649 + }
1650 + return dAtA[:n], nil
1651 +}
1652 +
1653 +func (m *ConnectionResponse) MarshalToVTStrict(dAtA []byte) (int, error) {
1654 + size := m.SizeVT()
1655 + return m.MarshalToSizedBufferVTStrict(dAtA[:size])
1656 +}
1657 +
1658 +func (m *ConnectionResponse) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1659 + if m == nil {
1660 + return 0, nil
1661 + }
1662 + i := len(dAtA)
1663 + _ = i
1664 + var l int
1665 + _ = l
1666 + if m.unknownFields != nil {
1667 + i -= len(m.unknownFields)
1668 + copy(dAtA[i:], m.unknownFields)
1669 + }
1670 + if m.Code != 0 {
1671 + i = protohelpers.EncodeVarint(dAtA, i, uint64(m.Code))
1672 + i--
1673 + dAtA[i] = 0x8
1674 + }
1675 + return len(dAtA) - i, nil
1676 +}
1677 +
1678 +func (m *Packet) SizeVT() (n int) {
1679 + if m == nil {
1680 + return 0
1681 + }
1682 + var l int
1683 + _ = l
1684 + if m.Type != 0 {
1685 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Type))
1686 + }
1687 + l = len(m.Payload)
1688 + if l > 0 {
1689 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1690 + }
1691 + n += len(m.unknownFields)
1692 + return n
1693 +}
1694 +
1695 +func (m *RelayInfo) SizeVT() (n int) {
1696 + if m == nil {
1697 + return 0
1698 + }
1699 + var l int
1700 + _ = l
1701 + if m.Identity != nil {
1702 + if size, ok := interface{}(m.Identity).(interface {
1703 + SizeVT() int
1704 + }); ok {
1705 + l = size.SizeVT()
1706 + } else {
1707 + l = proto.Size(m.Identity)
1708 + }
1709 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1710 + }
1711 + if len(m.Address) > 0 {
1712 + for _, s := range m.Address {
1713 + l = len(s)
1714 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1715 + }
1716 + }
1717 + if len(m.Leases) > 0 {
1718 + for _, s := range m.Leases {
1719 + l = len(s)
1720 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1721 + }
1722 + }
1723 + n += len(m.unknownFields)
1724 + return n
1725 +}
1726 +
1727 +func (m *RelayInfoRequest) SizeVT() (n int) {
1728 + if m == nil {
1729 + return 0
1730 + }
1731 + var l int
1732 + _ = l
1733 + n += len(m.unknownFields)
1734 + return n
1735 +}
1736 +
1737 +func (m *RelayInfoResponse) SizeVT() (n int) {
1738 + if m == nil {
1739 + return 0
1740 + }
1741 + var l int
1742 + _ = l
1743 + if m.RelayInfo != nil {
1744 + l = m.RelayInfo.SizeVT()
1745 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1746 + }
1747 + n += len(m.unknownFields)
1748 + return n
1749 +}
1750 +
1751 +func (m *Lease) SizeVT() (n int) {
1752 + if m == nil {
1753 + return 0
1754 + }
1755 + var l int
1756 + _ = l
1757 + if m.Identity != nil {
1758 + if size, ok := interface{}(m.Identity).(interface {
1759 + SizeVT() int
1760 + }); ok {
1761 + l = size.SizeVT()
1762 + } else {
1763 + l = proto.Size(m.Identity)
1764 + }
1765 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1766 + }
1767 + if m.Expires != 0 {
1768 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Expires))
1769 + }
1770 + l = len(m.Name)
1771 + if l > 0 {
1772 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1773 + }
1774 + if len(m.Alpn) > 0 {
1775 + for _, s := range m.Alpn {
1776 + l = len(s)
1777 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1778 + }
1779 + }
1780 + n += len(m.unknownFields)
1781 + return n
1782 +}
1783 +
1784 +func (m *LeaseUpdateRequest) SizeVT() (n int) {
1785 + if m == nil {
1786 + return 0
1787 + }
1788 + var l int
1789 + _ = l
1790 + if m.Lease != nil {
1791 + l = m.Lease.SizeVT()
1792 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1793 + }
1794 + l = len(m.Nonce)
1795 + if l > 0 {
1796 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1797 + }
1798 + if m.Timestamp != 0 {
1799 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Timestamp))
1800 + }
1801 + n += len(m.unknownFields)
1802 + return n
1803 +}
1804 +
1805 +func (m *LeaseUpdateResponse) SizeVT() (n int) {
1806 + if m == nil {
1807 + return 0
1808 + }
1809 + var l int
1810 + _ = l
1811 + if m.Code != 0 {
1812 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Code))
1813 + }
1814 + n += len(m.unknownFields)
1815 + return n
1816 +}
1817 +
1818 +func (m *LeaseDeleteRequest) SizeVT() (n int) {
1819 + if m == nil {
1820 + return 0
1821 + }
1822 + var l int
1823 + _ = l
1824 + if m.Identity != nil {
1825 + if size, ok := interface{}(m.Identity).(interface {
1826 + SizeVT() int
1827 + }); ok {
1828 + l = size.SizeVT()
1829 + } else {
1830 + l = proto.Size(m.Identity)
1831 + }
1832 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1833 + }
1834 + l = len(m.Nonce)
1835 + if l > 0 {
1836 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1837 + }
1838 + if m.Timestamp != 0 {
1839 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Timestamp))
1840 + }
1841 + n += len(m.unknownFields)
1842 + return n
1843 +}
1844 +
1845 +func (m *LeaseDeleteResponse) SizeVT() (n int) {
1846 + if m == nil {
1847 + return 0
1848 + }
1849 + var l int
1850 + _ = l
1851 + if m.Code != 0 {
1852 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Code))
1853 + }
1854 + n += len(m.unknownFields)
1855 + return n
1856 +}
1857 +
1858 +func (m *ConnectionRequest) SizeVT() (n int) {
1859 + if m == nil {
1860 + return 0
1861 + }
1862 + var l int
1863 + _ = l
1864 + l = len(m.LeaseId)
1865 + if l > 0 {
1866 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1867 + }
1868 + if m.ClientIdentity != nil {
1869 + if size, ok := interface{}(m.ClientIdentity).(interface {
1870 + SizeVT() int
1871 + }); ok {
1872 + l = size.SizeVT()
1873 + } else {
1874 + l = proto.Size(m.ClientIdentity)
1875 + }
1876 + n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1877 + }
1878 + n += len(m.unknownFields)
1879 + return n
1880 +}
1881 +
1882 +func (m *ConnectionResponse) SizeVT() (n int) {
1883 + if m == nil {
1884 + return 0
1885 + }
1886 + var l int
1887 + _ = l
1888 + if m.Code != 0 {
1889 + n += 1 + protohelpers.SizeOfVarint(uint64(m.Code))
1890 + }
1891 + n += len(m.unknownFields)
1892 + return n
1893 +}
1894 +
1895 +func (m *Packet) UnmarshalVT(dAtA []byte) error {
1896 + l := len(dAtA)
1897 + iNdEx := 0
1898 + for iNdEx < l {
1899 + preIndex := iNdEx
1900 + var wire uint64
1901 + for shift := uint(0); ; shift += 7 {
1902 + if shift >= 64 {
1903 + return protohelpers.ErrIntOverflow
1904 + }
1905 + if iNdEx >= l {
1906 + return io.ErrUnexpectedEOF
1907 + }
1908 + b := dAtA[iNdEx]
1909 + iNdEx++
1910 + wire |= uint64(b&0x7F) << shift
1911 + if b < 0x80 {
1912 + break
1913 + }
1914 + }
1915 + fieldNum := int32(wire >> 3)
1916 + wireType := int(wire & 0x7)
1917 + if wireType == 4 {
1918 + return fmt.Errorf("proto: Packet: wiretype end group for non-group")
1919 + }
1920 + if fieldNum <= 0 {
1921 + return fmt.Errorf("proto: Packet: illegal tag %d (wire type %d)", fieldNum, wire)
1922 + }
1923 + switch fieldNum {
1924 + case 1:
1925 + if wireType != 0 {
1926 + return fmt.Errorf("proto: wrong wireType = %d for field Type", wireType)
1927 + }
1928 + m.Type = 0
1929 + for shift := uint(0); ; shift += 7 {
1930 + if shift >= 64 {
1931 + return protohelpers.ErrIntOverflow
1932 + }
1933 + if iNdEx >= l {
1934 + return io.ErrUnexpectedEOF
1935 + }
1936 + b := dAtA[iNdEx]
1937 + iNdEx++
1938 + m.Type |= PacketType(b&0x7F) << shift
1939 + if b < 0x80 {
1940 + break
1941 + }
1942 + }
1943 + case 2:
1944 + if wireType != 2 {
1945 + return fmt.Errorf("proto: wrong wireType = %d for field Payload", wireType)
1946 + }
1947 + var byteLen int
1948 + for shift := uint(0); ; shift += 7 {
1949 + if shift >= 64 {
1950 + return protohelpers.ErrIntOverflow
1951 + }
1952 + if iNdEx >= l {
1953 + return io.ErrUnexpectedEOF
1954 + }
1955 + b := dAtA[iNdEx]
1956 + iNdEx++
1957 + byteLen |= int(b&0x7F) << shift
1958 + if b < 0x80 {
1959 + break
1960 + }
1961 + }
1962 + if byteLen < 0 {
1963 + return protohelpers.ErrInvalidLength
1964 + }
1965 + postIndex := iNdEx + byteLen
1966 + if postIndex < 0 {
1967 + return protohelpers.ErrInvalidLength
1968 + }
1969 + if postIndex > l {
1970 + return io.ErrUnexpectedEOF
1971 + }
1972 + m.Payload = append(m.Payload[:0], dAtA[iNdEx:postIndex]...)
1973 + if m.Payload == nil {
1974 + m.Payload = []byte{}
1975 + }
1976 + iNdEx = postIndex
1977 + default:
1978 + iNdEx = preIndex
1979 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
1980 + if err != nil {
1981 + return err
1982 + }
1983 + if (skippy < 0) || (iNdEx+skippy) < 0 {
1984 + return protohelpers.ErrInvalidLength
1985 + }
1986 + if (iNdEx + skippy) > l {
1987 + return io.ErrUnexpectedEOF
1988 + }
1989 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
1990 + iNdEx += skippy
1991 + }
1992 + }
1993 +
1994 + if iNdEx > l {
1995 + return io.ErrUnexpectedEOF
1996 + }
1997 + return nil
1998 +}
1999 +func (m *RelayInfo) UnmarshalVT(dAtA []byte) error {
2000 + l := len(dAtA)
2001 + iNdEx := 0
2002 + for iNdEx < l {
2003 + preIndex := iNdEx
2004 + var wire uint64
2005 + for shift := uint(0); ; shift += 7 {
2006 + if shift >= 64 {
2007 + return protohelpers.ErrIntOverflow
2008 + }
2009 + if iNdEx >= l {
2010 + return io.ErrUnexpectedEOF
2011 + }
2012 + b := dAtA[iNdEx]
2013 + iNdEx++
2014 + wire |= uint64(b&0x7F) << shift
2015 + if b < 0x80 {
2016 + break
2017 + }
2018 + }
2019 + fieldNum := int32(wire >> 3)
2020 + wireType := int(wire & 0x7)
2021 + if wireType == 4 {
2022 + return fmt.Errorf("proto: RelayInfo: wiretype end group for non-group")
2023 + }
2024 + if fieldNum <= 0 {
2025 + return fmt.Errorf("proto: RelayInfo: illegal tag %d (wire type %d)", fieldNum, wire)
2026 + }
2027 + switch fieldNum {
2028 + case 1:
2029 + if wireType != 2 {
2030 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
2031 + }
2032 + var msglen int
2033 + for shift := uint(0); ; shift += 7 {
2034 + if shift >= 64 {
2035 + return protohelpers.ErrIntOverflow
2036 + }
2037 + if iNdEx >= l {
2038 + return io.ErrUnexpectedEOF
2039 + }
2040 + b := dAtA[iNdEx]
2041 + iNdEx++
2042 + msglen |= int(b&0x7F) << shift
2043 + if b < 0x80 {
2044 + break
2045 + }
2046 + }
2047 + if msglen < 0 {
2048 + return protohelpers.ErrInvalidLength
2049 + }
2050 + postIndex := iNdEx + msglen
2051 + if postIndex < 0 {
2052 + return protohelpers.ErrInvalidLength
2053 + }
2054 + if postIndex > l {
2055 + return io.ErrUnexpectedEOF
2056 + }
2057 + if m.Identity == nil {
2058 + m.Identity = &rdsec.Identity{}
2059 + }
2060 + if unmarshal, ok := interface{}(m.Identity).(interface {
2061 + UnmarshalVT([]byte) error
2062 + }); ok {
2063 + if err := unmarshal.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2064 + return err
2065 + }
2066 + } else {
2067 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
2068 + return err
2069 + }
2070 + }
2071 + iNdEx = postIndex
2072 + case 2:
2073 + if wireType != 2 {
2074 + return fmt.Errorf("proto: wrong wireType = %d for field Address", wireType)
2075 + }
2076 + var stringLen uint64
2077 + for shift := uint(0); ; shift += 7 {
2078 + if shift >= 64 {
2079 + return protohelpers.ErrIntOverflow
2080 + }
2081 + if iNdEx >= l {
2082 + return io.ErrUnexpectedEOF
2083 + }
2084 + b := dAtA[iNdEx]
2085 + iNdEx++
2086 + stringLen |= uint64(b&0x7F) << shift
2087 + if b < 0x80 {
2088 + break
2089 + }
2090 + }
2091 + intStringLen := int(stringLen)
2092 + if intStringLen < 0 {
2093 + return protohelpers.ErrInvalidLength
2094 + }
2095 + postIndex := iNdEx + intStringLen
2096 + if postIndex < 0 {
2097 + return protohelpers.ErrInvalidLength
2098 + }
2099 + if postIndex > l {
2100 + return io.ErrUnexpectedEOF
2101 + }
2102 + m.Address = append(m.Address, string(dAtA[iNdEx:postIndex]))
2103 + iNdEx = postIndex
2104 + case 3:
2105 + if wireType != 2 {
2106 + return fmt.Errorf("proto: wrong wireType = %d for field Leases", wireType)
2107 + }
2108 + var stringLen uint64
2109 + for shift := uint(0); ; shift += 7 {
2110 + if shift >= 64 {
2111 + return protohelpers.ErrIntOverflow
2112 + }
2113 + if iNdEx >= l {
2114 + return io.ErrUnexpectedEOF
2115 + }
2116 + b := dAtA[iNdEx]
2117 + iNdEx++
2118 + stringLen |= uint64(b&0x7F) << shift
2119 + if b < 0x80 {
2120 + break
2121 + }
2122 + }
2123 + intStringLen := int(stringLen)
2124 + if intStringLen < 0 {
2125 + return protohelpers.ErrInvalidLength
2126 + }
2127 + postIndex := iNdEx + intStringLen
2128 + if postIndex < 0 {
2129 + return protohelpers.ErrInvalidLength
2130 + }
2131 + if postIndex > l {
2132 + return io.ErrUnexpectedEOF
2133 + }
2134 + m.Leases = append(m.Leases, string(dAtA[iNdEx:postIndex]))
2135 + iNdEx = postIndex
2136 + default:
2137 + iNdEx = preIndex
2138 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2139 + if err != nil {
2140 + return err
2141 + }
2142 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2143 + return protohelpers.ErrInvalidLength
2144 + }
2145 + if (iNdEx + skippy) > l {
2146 + return io.ErrUnexpectedEOF
2147 + }
2148 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2149 + iNdEx += skippy
2150 + }
2151 + }
2152 +
2153 + if iNdEx > l {
2154 + return io.ErrUnexpectedEOF
2155 + }
2156 + return nil
2157 +}
2158 +func (m *RelayInfoRequest) UnmarshalVT(dAtA []byte) error {
2159 + l := len(dAtA)
2160 + iNdEx := 0
2161 + for iNdEx < l {
2162 + preIndex := iNdEx
2163 + var wire uint64
2164 + for shift := uint(0); ; shift += 7 {
2165 + if shift >= 64 {
2166 + return protohelpers.ErrIntOverflow
2167 + }
2168 + if iNdEx >= l {
2169 + return io.ErrUnexpectedEOF
2170 + }
2171 + b := dAtA[iNdEx]
2172 + iNdEx++
2173 + wire |= uint64(b&0x7F) << shift
2174 + if b < 0x80 {
2175 + break
2176 + }
2177 + }
2178 + fieldNum := int32(wire >> 3)
2179 + wireType := int(wire & 0x7)
2180 + if wireType == 4 {
2181 + return fmt.Errorf("proto: RelayInfoRequest: wiretype end group for non-group")
2182 + }
2183 + if fieldNum <= 0 {
2184 + return fmt.Errorf("proto: RelayInfoRequest: illegal tag %d (wire type %d)", fieldNum, wire)
2185 + }
2186 + switch fieldNum {
2187 + default:
2188 + iNdEx = preIndex
2189 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2190 + if err != nil {
2191 + return err
2192 + }
2193 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2194 + return protohelpers.ErrInvalidLength
2195 + }
2196 + if (iNdEx + skippy) > l {
2197 + return io.ErrUnexpectedEOF
2198 + }
2199 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2200 + iNdEx += skippy
2201 + }
2202 + }
2203 +
2204 + if iNdEx > l {
2205 + return io.ErrUnexpectedEOF
2206 + }
2207 + return nil
2208 +}
2209 +func (m *RelayInfoResponse) UnmarshalVT(dAtA []byte) error {
2210 + l := len(dAtA)
2211 + iNdEx := 0
2212 + for iNdEx < l {
2213 + preIndex := iNdEx
2214 + var wire uint64
2215 + for shift := uint(0); ; shift += 7 {
2216 + if shift >= 64 {
2217 + return protohelpers.ErrIntOverflow
2218 + }
2219 + if iNdEx >= l {
2220 + return io.ErrUnexpectedEOF
2221 + }
2222 + b := dAtA[iNdEx]
2223 + iNdEx++
2224 + wire |= uint64(b&0x7F) << shift
2225 + if b < 0x80 {
2226 + break
2227 + }
2228 + }
2229 + fieldNum := int32(wire >> 3)
2230 + wireType := int(wire & 0x7)
2231 + if wireType == 4 {
2232 + return fmt.Errorf("proto: RelayInfoResponse: wiretype end group for non-group")
2233 + }
2234 + if fieldNum <= 0 {
2235 + return fmt.Errorf("proto: RelayInfoResponse: illegal tag %d (wire type %d)", fieldNum, wire)
2236 + }
2237 + switch fieldNum {
2238 + case 1:
2239 + if wireType != 2 {
2240 + return fmt.Errorf("proto: wrong wireType = %d for field RelayInfo", wireType)
2241 + }
2242 + var msglen int
2243 + for shift := uint(0); ; shift += 7 {
2244 + if shift >= 64 {
2245 + return protohelpers.ErrIntOverflow
2246 + }
2247 + if iNdEx >= l {
2248 + return io.ErrUnexpectedEOF
2249 + }
2250 + b := dAtA[iNdEx]
2251 + iNdEx++
2252 + msglen |= int(b&0x7F) << shift
2253 + if b < 0x80 {
2254 + break
2255 + }
2256 + }
2257 + if msglen < 0 {
2258 + return protohelpers.ErrInvalidLength
2259 + }
2260 + postIndex := iNdEx + msglen
2261 + if postIndex < 0 {
2262 + return protohelpers.ErrInvalidLength
2263 + }
2264 + if postIndex > l {
2265 + return io.ErrUnexpectedEOF
2266 + }
2267 + if m.RelayInfo == nil {
2268 + m.RelayInfo = &RelayInfo{}
2269 + }
2270 + if err := m.RelayInfo.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2271 + return err
2272 + }
2273 + iNdEx = postIndex
2274 + default:
2275 + iNdEx = preIndex
2276 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2277 + if err != nil {
2278 + return err
2279 + }
2280 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2281 + return protohelpers.ErrInvalidLength
2282 + }
2283 + if (iNdEx + skippy) > l {
2284 + return io.ErrUnexpectedEOF
2285 + }
2286 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2287 + iNdEx += skippy
2288 + }
2289 + }
2290 +
2291 + if iNdEx > l {
2292 + return io.ErrUnexpectedEOF
2293 + }
2294 + return nil
2295 +}
2296 +func (m *Lease) UnmarshalVT(dAtA []byte) error {
2297 + l := len(dAtA)
2298 + iNdEx := 0
2299 + for iNdEx < l {
2300 + preIndex := iNdEx
2301 + var wire uint64
2302 + for shift := uint(0); ; shift += 7 {
2303 + if shift >= 64 {
2304 + return protohelpers.ErrIntOverflow
2305 + }
2306 + if iNdEx >= l {
2307 + return io.ErrUnexpectedEOF
2308 + }
2309 + b := dAtA[iNdEx]
2310 + iNdEx++
2311 + wire |= uint64(b&0x7F) << shift
2312 + if b < 0x80 {
2313 + break
2314 + }
2315 + }
2316 + fieldNum := int32(wire >> 3)
2317 + wireType := int(wire & 0x7)
2318 + if wireType == 4 {
2319 + return fmt.Errorf("proto: Lease: wiretype end group for non-group")
2320 + }
2321 + if fieldNum <= 0 {
2322 + return fmt.Errorf("proto: Lease: illegal tag %d (wire type %d)", fieldNum, wire)
2323 + }
2324 + switch fieldNum {
2325 + case 1:
2326 + if wireType != 2 {
2327 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
2328 + }
2329 + var msglen int
2330 + for shift := uint(0); ; shift += 7 {
2331 + if shift >= 64 {
2332 + return protohelpers.ErrIntOverflow
2333 + }
2334 + if iNdEx >= l {
2335 + return io.ErrUnexpectedEOF
2336 + }
2337 + b := dAtA[iNdEx]
2338 + iNdEx++
2339 + msglen |= int(b&0x7F) << shift
2340 + if b < 0x80 {
2341 + break
2342 + }
2343 + }
2344 + if msglen < 0 {
2345 + return protohelpers.ErrInvalidLength
2346 + }
2347 + postIndex := iNdEx + msglen
2348 + if postIndex < 0 {
2349 + return protohelpers.ErrInvalidLength
2350 + }
2351 + if postIndex > l {
2352 + return io.ErrUnexpectedEOF
2353 + }
2354 + if m.Identity == nil {
2355 + m.Identity = &rdsec.Identity{}
2356 + }
2357 + if unmarshal, ok := interface{}(m.Identity).(interface {
2358 + UnmarshalVT([]byte) error
2359 + }); ok {
2360 + if err := unmarshal.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2361 + return err
2362 + }
2363 + } else {
2364 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
2365 + return err
2366 + }
2367 + }
2368 + iNdEx = postIndex
2369 + case 2:
2370 + if wireType != 0 {
2371 + return fmt.Errorf("proto: wrong wireType = %d for field Expires", wireType)
2372 + }
2373 + m.Expires = 0
2374 + for shift := uint(0); ; shift += 7 {
2375 + if shift >= 64 {
2376 + return protohelpers.ErrIntOverflow
2377 + }
2378 + if iNdEx >= l {
2379 + return io.ErrUnexpectedEOF
2380 + }
2381 + b := dAtA[iNdEx]
2382 + iNdEx++
2383 + m.Expires |= int64(b&0x7F) << shift
2384 + if b < 0x80 {
2385 + break
2386 + }
2387 + }
2388 + case 3:
2389 + if wireType != 2 {
2390 + return fmt.Errorf("proto: wrong wireType = %d for field Name", wireType)
2391 + }
2392 + var stringLen uint64
2393 + for shift := uint(0); ; shift += 7 {
2394 + if shift >= 64 {
2395 + return protohelpers.ErrIntOverflow
2396 + }
2397 + if iNdEx >= l {
2398 + return io.ErrUnexpectedEOF
2399 + }
2400 + b := dAtA[iNdEx]
2401 + iNdEx++
2402 + stringLen |= uint64(b&0x7F) << shift
2403 + if b < 0x80 {
2404 + break
2405 + }
2406 + }
2407 + intStringLen := int(stringLen)
2408 + if intStringLen < 0 {
2409 + return protohelpers.ErrInvalidLength
2410 + }
2411 + postIndex := iNdEx + intStringLen
2412 + if postIndex < 0 {
2413 + return protohelpers.ErrInvalidLength
2414 + }
2415 + if postIndex > l {
2416 + return io.ErrUnexpectedEOF
2417 + }
2418 + m.Name = string(dAtA[iNdEx:postIndex])
2419 + iNdEx = postIndex
2420 + case 4:
2421 + if wireType != 2 {
2422 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
2423 + }
2424 + var stringLen uint64
2425 + for shift := uint(0); ; shift += 7 {
2426 + if shift >= 64 {
2427 + return protohelpers.ErrIntOverflow
2428 + }
2429 + if iNdEx >= l {
2430 + return io.ErrUnexpectedEOF
2431 + }
2432 + b := dAtA[iNdEx]
2433 + iNdEx++
2434 + stringLen |= uint64(b&0x7F) << shift
2435 + if b < 0x80 {
2436 + break
2437 + }
2438 + }
2439 + intStringLen := int(stringLen)
2440 + if intStringLen < 0 {
2441 + return protohelpers.ErrInvalidLength
2442 + }
2443 + postIndex := iNdEx + intStringLen
2444 + if postIndex < 0 {
2445 + return protohelpers.ErrInvalidLength
2446 + }
2447 + if postIndex > l {
2448 + return io.ErrUnexpectedEOF
2449 + }
2450 + m.Alpn = append(m.Alpn, string(dAtA[iNdEx:postIndex]))
2451 + iNdEx = postIndex
2452 + default:
2453 + iNdEx = preIndex
2454 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2455 + if err != nil {
2456 + return err
2457 + }
2458 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2459 + return protohelpers.ErrInvalidLength
2460 + }
2461 + if (iNdEx + skippy) > l {
2462 + return io.ErrUnexpectedEOF
2463 + }
2464 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2465 + iNdEx += skippy
2466 + }
2467 + }
2468 +
2469 + if iNdEx > l {
2470 + return io.ErrUnexpectedEOF
2471 + }
2472 + return nil
2473 +}
2474 +func (m *LeaseUpdateRequest) UnmarshalVT(dAtA []byte) error {
2475 + l := len(dAtA)
2476 + iNdEx := 0
2477 + for iNdEx < l {
2478 + preIndex := iNdEx
2479 + var wire uint64
2480 + for shift := uint(0); ; shift += 7 {
2481 + if shift >= 64 {
2482 + return protohelpers.ErrIntOverflow
2483 + }
2484 + if iNdEx >= l {
2485 + return io.ErrUnexpectedEOF
2486 + }
2487 + b := dAtA[iNdEx]
2488 + iNdEx++
2489 + wire |= uint64(b&0x7F) << shift
2490 + if b < 0x80 {
2491 + break
2492 + }
2493 + }
2494 + fieldNum := int32(wire >> 3)
2495 + wireType := int(wire & 0x7)
2496 + if wireType == 4 {
2497 + return fmt.Errorf("proto: LeaseUpdateRequest: wiretype end group for non-group")
2498 + }
2499 + if fieldNum <= 0 {
2500 + return fmt.Errorf("proto: LeaseUpdateRequest: illegal tag %d (wire type %d)", fieldNum, wire)
2501 + }
2502 + switch fieldNum {
2503 + case 1:
2504 + if wireType != 2 {
2505 + return fmt.Errorf("proto: wrong wireType = %d for field Lease", wireType)
2506 + }
2507 + var msglen int
2508 + for shift := uint(0); ; shift += 7 {
2509 + if shift >= 64 {
2510 + return protohelpers.ErrIntOverflow
2511 + }
2512 + if iNdEx >= l {
2513 + return io.ErrUnexpectedEOF
2514 + }
2515 + b := dAtA[iNdEx]
2516 + iNdEx++
2517 + msglen |= int(b&0x7F) << shift
2518 + if b < 0x80 {
2519 + break
2520 + }
2521 + }
2522 + if msglen < 0 {
2523 + return protohelpers.ErrInvalidLength
2524 + }
2525 + postIndex := iNdEx + msglen
2526 + if postIndex < 0 {
2527 + return protohelpers.ErrInvalidLength
2528 + }
2529 + if postIndex > l {
2530 + return io.ErrUnexpectedEOF
2531 + }
2532 + if m.Lease == nil {
2533 + m.Lease = &Lease{}
2534 + }
2535 + if err := m.Lease.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2536 + return err
2537 + }
2538 + iNdEx = postIndex
2539 + case 2:
2540 + if wireType != 2 {
2541 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
2542 + }
2543 + var byteLen int
2544 + for shift := uint(0); ; shift += 7 {
2545 + if shift >= 64 {
2546 + return protohelpers.ErrIntOverflow
2547 + }
2548 + if iNdEx >= l {
2549 + return io.ErrUnexpectedEOF
2550 + }
2551 + b := dAtA[iNdEx]
2552 + iNdEx++
2553 + byteLen |= int(b&0x7F) << shift
2554 + if b < 0x80 {
2555 + break
2556 + }
2557 + }
2558 + if byteLen < 0 {
2559 + return protohelpers.ErrInvalidLength
2560 + }
2561 + postIndex := iNdEx + byteLen
2562 + if postIndex < 0 {
2563 + return protohelpers.ErrInvalidLength
2564 + }
2565 + if postIndex > l {
2566 + return io.ErrUnexpectedEOF
2567 + }
2568 + m.Nonce = append(m.Nonce[:0], dAtA[iNdEx:postIndex]...)
2569 + if m.Nonce == nil {
2570 + m.Nonce = []byte{}
2571 + }
2572 + iNdEx = postIndex
2573 + case 3:
2574 + if wireType != 0 {
2575 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
2576 + }
2577 + m.Timestamp = 0
2578 + for shift := uint(0); ; shift += 7 {
2579 + if shift >= 64 {
2580 + return protohelpers.ErrIntOverflow
2581 + }
2582 + if iNdEx >= l {
2583 + return io.ErrUnexpectedEOF
2584 + }
2585 + b := dAtA[iNdEx]
2586 + iNdEx++
2587 + m.Timestamp |= int64(b&0x7F) << shift
2588 + if b < 0x80 {
2589 + break
2590 + }
2591 + }
2592 + default:
2593 + iNdEx = preIndex
2594 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2595 + if err != nil {
2596 + return err
2597 + }
2598 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2599 + return protohelpers.ErrInvalidLength
2600 + }
2601 + if (iNdEx + skippy) > l {
2602 + return io.ErrUnexpectedEOF
2603 + }
2604 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2605 + iNdEx += skippy
2606 + }
2607 + }
2608 +
2609 + if iNdEx > l {
2610 + return io.ErrUnexpectedEOF
2611 + }
2612 + return nil
2613 +}
2614 +func (m *LeaseUpdateResponse) UnmarshalVT(dAtA []byte) error {
2615 + l := len(dAtA)
2616 + iNdEx := 0
2617 + for iNdEx < l {
2618 + preIndex := iNdEx
2619 + var wire uint64
2620 + for shift := uint(0); ; shift += 7 {
2621 + if shift >= 64 {
2622 + return protohelpers.ErrIntOverflow
2623 + }
2624 + if iNdEx >= l {
2625 + return io.ErrUnexpectedEOF
2626 + }
2627 + b := dAtA[iNdEx]
2628 + iNdEx++
2629 + wire |= uint64(b&0x7F) << shift
2630 + if b < 0x80 {
2631 + break
2632 + }
2633 + }
2634 + fieldNum := int32(wire >> 3)
2635 + wireType := int(wire & 0x7)
2636 + if wireType == 4 {
2637 + return fmt.Errorf("proto: LeaseUpdateResponse: wiretype end group for non-group")
2638 + }
2639 + if fieldNum <= 0 {
2640 + return fmt.Errorf("proto: LeaseUpdateResponse: illegal tag %d (wire type %d)", fieldNum, wire)
2641 + }
2642 + switch fieldNum {
2643 + case 1:
2644 + if wireType != 0 {
2645 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
2646 + }
2647 + m.Code = 0
2648 + for shift := uint(0); ; shift += 7 {
2649 + if shift >= 64 {
2650 + return protohelpers.ErrIntOverflow
2651 + }
2652 + if iNdEx >= l {
2653 + return io.ErrUnexpectedEOF
2654 + }
2655 + b := dAtA[iNdEx]
2656 + iNdEx++
2657 + m.Code |= ResponseCode(b&0x7F) << shift
2658 + if b < 0x80 {
2659 + break
2660 + }
2661 + }
2662 + default:
2663 + iNdEx = preIndex
2664 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2665 + if err != nil {
2666 + return err
2667 + }
2668 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2669 + return protohelpers.ErrInvalidLength
2670 + }
2671 + if (iNdEx + skippy) > l {
2672 + return io.ErrUnexpectedEOF
2673 + }
2674 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2675 + iNdEx += skippy
2676 + }
2677 + }
2678 +
2679 + if iNdEx > l {
2680 + return io.ErrUnexpectedEOF
2681 + }
2682 + return nil
2683 +}
2684 +func (m *LeaseDeleteRequest) UnmarshalVT(dAtA []byte) error {
2685 + l := len(dAtA)
2686 + iNdEx := 0
2687 + for iNdEx < l {
2688 + preIndex := iNdEx
2689 + var wire uint64
2690 + for shift := uint(0); ; shift += 7 {
2691 + if shift >= 64 {
2692 + return protohelpers.ErrIntOverflow
2693 + }
2694 + if iNdEx >= l {
2695 + return io.ErrUnexpectedEOF
2696 + }
2697 + b := dAtA[iNdEx]
2698 + iNdEx++
2699 + wire |= uint64(b&0x7F) << shift
2700 + if b < 0x80 {
2701 + break
2702 + }
2703 + }
2704 + fieldNum := int32(wire >> 3)
2705 + wireType := int(wire & 0x7)
2706 + if wireType == 4 {
2707 + return fmt.Errorf("proto: LeaseDeleteRequest: wiretype end group for non-group")
2708 + }
2709 + if fieldNum <= 0 {
2710 + return fmt.Errorf("proto: LeaseDeleteRequest: illegal tag %d (wire type %d)", fieldNum, wire)
2711 + }
2712 + switch fieldNum {
2713 + case 1:
2714 + if wireType != 2 {
2715 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
2716 + }
2717 + var msglen int
2718 + for shift := uint(0); ; shift += 7 {
2719 + if shift >= 64 {
2720 + return protohelpers.ErrIntOverflow
2721 + }
2722 + if iNdEx >= l {
2723 + return io.ErrUnexpectedEOF
2724 + }
2725 + b := dAtA[iNdEx]
2726 + iNdEx++
2727 + msglen |= int(b&0x7F) << shift
2728 + if b < 0x80 {
2729 + break
2730 + }
2731 + }
2732 + if msglen < 0 {
2733 + return protohelpers.ErrInvalidLength
2734 + }
2735 + postIndex := iNdEx + msglen
2736 + if postIndex < 0 {
2737 + return protohelpers.ErrInvalidLength
2738 + }
2739 + if postIndex > l {
2740 + return io.ErrUnexpectedEOF
2741 + }
2742 + if m.Identity == nil {
2743 + m.Identity = &rdsec.Identity{}
2744 + }
2745 + if unmarshal, ok := interface{}(m.Identity).(interface {
2746 + UnmarshalVT([]byte) error
2747 + }); ok {
2748 + if err := unmarshal.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2749 + return err
2750 + }
2751 + } else {
2752 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
2753 + return err
2754 + }
2755 + }
2756 + iNdEx = postIndex
2757 + case 2:
2758 + if wireType != 2 {
2759 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
2760 + }
2761 + var byteLen int
2762 + for shift := uint(0); ; shift += 7 {
2763 + if shift >= 64 {
2764 + return protohelpers.ErrIntOverflow
2765 + }
2766 + if iNdEx >= l {
2767 + return io.ErrUnexpectedEOF
2768 + }
2769 + b := dAtA[iNdEx]
2770 + iNdEx++
2771 + byteLen |= int(b&0x7F) << shift
2772 + if b < 0x80 {
2773 + break
2774 + }
2775 + }
2776 + if byteLen < 0 {
2777 + return protohelpers.ErrInvalidLength
2778 + }
2779 + postIndex := iNdEx + byteLen
2780 + if postIndex < 0 {
2781 + return protohelpers.ErrInvalidLength
2782 + }
2783 + if postIndex > l {
2784 + return io.ErrUnexpectedEOF
2785 + }
2786 + m.Nonce = append(m.Nonce[:0], dAtA[iNdEx:postIndex]...)
2787 + if m.Nonce == nil {
2788 + m.Nonce = []byte{}
2789 + }
2790 + iNdEx = postIndex
2791 + case 3:
2792 + if wireType != 0 {
2793 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
2794 + }
2795 + m.Timestamp = 0
2796 + for shift := uint(0); ; shift += 7 {
2797 + if shift >= 64 {
2798 + return protohelpers.ErrIntOverflow
2799 + }
2800 + if iNdEx >= l {
2801 + return io.ErrUnexpectedEOF
2802 + }
2803 + b := dAtA[iNdEx]
2804 + iNdEx++
2805 + m.Timestamp |= int64(b&0x7F) << shift
2806 + if b < 0x80 {
2807 + break
2808 + }
2809 + }
2810 + default:
2811 + iNdEx = preIndex
2812 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2813 + if err != nil {
2814 + return err
2815 + }
2816 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2817 + return protohelpers.ErrInvalidLength
2818 + }
2819 + if (iNdEx + skippy) > l {
2820 + return io.ErrUnexpectedEOF
2821 + }
2822 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2823 + iNdEx += skippy
2824 + }
2825 + }
2826 +
2827 + if iNdEx > l {
2828 + return io.ErrUnexpectedEOF
2829 + }
2830 + return nil
2831 +}
2832 +func (m *LeaseDeleteResponse) UnmarshalVT(dAtA []byte) error {
2833 + l := len(dAtA)
2834 + iNdEx := 0
2835 + for iNdEx < l {
2836 + preIndex := iNdEx
2837 + var wire uint64
2838 + for shift := uint(0); ; shift += 7 {
2839 + if shift >= 64 {
2840 + return protohelpers.ErrIntOverflow
2841 + }
2842 + if iNdEx >= l {
2843 + return io.ErrUnexpectedEOF
2844 + }
2845 + b := dAtA[iNdEx]
2846 + iNdEx++
2847 + wire |= uint64(b&0x7F) << shift
2848 + if b < 0x80 {
2849 + break
2850 + }
2851 + }
2852 + fieldNum := int32(wire >> 3)
2853 + wireType := int(wire & 0x7)
2854 + if wireType == 4 {
2855 + return fmt.Errorf("proto: LeaseDeleteResponse: wiretype end group for non-group")
2856 + }
2857 + if fieldNum <= 0 {
2858 + return fmt.Errorf("proto: LeaseDeleteResponse: illegal tag %d (wire type %d)", fieldNum, wire)
2859 + }
2860 + switch fieldNum {
2861 + case 1:
2862 + if wireType != 0 {
2863 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
2864 + }
2865 + m.Code = 0
2866 + for shift := uint(0); ; shift += 7 {
2867 + if shift >= 64 {
2868 + return protohelpers.ErrIntOverflow
2869 + }
2870 + if iNdEx >= l {
2871 + return io.ErrUnexpectedEOF
2872 + }
2873 + b := dAtA[iNdEx]
2874 + iNdEx++
2875 + m.Code |= ResponseCode(b&0x7F) << shift
2876 + if b < 0x80 {
2877 + break
2878 + }
2879 + }
2880 + default:
2881 + iNdEx = preIndex
2882 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
2883 + if err != nil {
2884 + return err
2885 + }
2886 + if (skippy < 0) || (iNdEx+skippy) < 0 {
2887 + return protohelpers.ErrInvalidLength
2888 + }
2889 + if (iNdEx + skippy) > l {
2890 + return io.ErrUnexpectedEOF
2891 + }
2892 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
2893 + iNdEx += skippy
2894 + }
2895 + }
2896 +
2897 + if iNdEx > l {
2898 + return io.ErrUnexpectedEOF
2899 + }
2900 + return nil
2901 +}
2902 +func (m *ConnectionRequest) UnmarshalVT(dAtA []byte) error {
2903 + l := len(dAtA)
2904 + iNdEx := 0
2905 + for iNdEx < l {
2906 + preIndex := iNdEx
2907 + var wire uint64
2908 + for shift := uint(0); ; shift += 7 {
2909 + if shift >= 64 {
2910 + return protohelpers.ErrIntOverflow
2911 + }
2912 + if iNdEx >= l {
2913 + return io.ErrUnexpectedEOF
2914 + }
2915 + b := dAtA[iNdEx]
2916 + iNdEx++
2917 + wire |= uint64(b&0x7F) << shift
2918 + if b < 0x80 {
2919 + break
2920 + }
2921 + }
2922 + fieldNum := int32(wire >> 3)
2923 + wireType := int(wire & 0x7)
2924 + if wireType == 4 {
2925 + return fmt.Errorf("proto: ConnectionRequest: wiretype end group for non-group")
2926 + }
2927 + if fieldNum <= 0 {
2928 + return fmt.Errorf("proto: ConnectionRequest: illegal tag %d (wire type %d)", fieldNum, wire)
2929 + }
2930 + switch fieldNum {
2931 + case 1:
2932 + if wireType != 2 {
2933 + return fmt.Errorf("proto: wrong wireType = %d for field LeaseId", wireType)
2934 + }
2935 + var stringLen uint64
2936 + for shift := uint(0); ; shift += 7 {
2937 + if shift >= 64 {
2938 + return protohelpers.ErrIntOverflow
2939 + }
2940 + if iNdEx >= l {
2941 + return io.ErrUnexpectedEOF
2942 + }
2943 + b := dAtA[iNdEx]
2944 + iNdEx++
2945 + stringLen |= uint64(b&0x7F) << shift
2946 + if b < 0x80 {
2947 + break
2948 + }
2949 + }
2950 + intStringLen := int(stringLen)
2951 + if intStringLen < 0 {
2952 + return protohelpers.ErrInvalidLength
2953 + }
2954 + postIndex := iNdEx + intStringLen
2955 + if postIndex < 0 {
2956 + return protohelpers.ErrInvalidLength
2957 + }
2958 + if postIndex > l {
2959 + return io.ErrUnexpectedEOF
2960 + }
2961 + m.LeaseId = string(dAtA[iNdEx:postIndex])
2962 + iNdEx = postIndex
2963 + case 2:
2964 + if wireType != 2 {
2965 + return fmt.Errorf("proto: wrong wireType = %d for field ClientIdentity", wireType)
2966 + }
2967 + var msglen int
2968 + for shift := uint(0); ; shift += 7 {
2969 + if shift >= 64 {
2970 + return protohelpers.ErrIntOverflow
2971 + }
2972 + if iNdEx >= l {
2973 + return io.ErrUnexpectedEOF
2974 + }
2975 + b := dAtA[iNdEx]
2976 + iNdEx++
2977 + msglen |= int(b&0x7F) << shift
2978 + if b < 0x80 {
2979 + break
2980 + }
2981 + }
2982 + if msglen < 0 {
2983 + return protohelpers.ErrInvalidLength
2984 + }
2985 + postIndex := iNdEx + msglen
2986 + if postIndex < 0 {
2987 + return protohelpers.ErrInvalidLength
2988 + }
2989 + if postIndex > l {
2990 + return io.ErrUnexpectedEOF
2991 + }
2992 + if m.ClientIdentity == nil {
2993 + m.ClientIdentity = &rdsec.Identity{}
2994 + }
2995 + if unmarshal, ok := interface{}(m.ClientIdentity).(interface {
2996 + UnmarshalVT([]byte) error
2997 + }); ok {
2998 + if err := unmarshal.UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2999 + return err
3000 + }
3001 + } else {
3002 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.ClientIdentity); err != nil {
3003 + return err
3004 + }
3005 + }
3006 + iNdEx = postIndex
3007 + default:
3008 + iNdEx = preIndex
3009 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3010 + if err != nil {
3011 + return err
3012 + }
3013 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3014 + return protohelpers.ErrInvalidLength
3015 + }
3016 + if (iNdEx + skippy) > l {
3017 + return io.ErrUnexpectedEOF
3018 + }
3019 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3020 + iNdEx += skippy
3021 + }
3022 + }
3023 +
3024 + if iNdEx > l {
3025 + return io.ErrUnexpectedEOF
3026 + }
3027 + return nil
3028 +}
3029 +func (m *ConnectionResponse) UnmarshalVT(dAtA []byte) error {
3030 + l := len(dAtA)
3031 + iNdEx := 0
3032 + for iNdEx < l {
3033 + preIndex := iNdEx
3034 + var wire uint64
3035 + for shift := uint(0); ; shift += 7 {
3036 + if shift >= 64 {
3037 + return protohelpers.ErrIntOverflow
3038 + }
3039 + if iNdEx >= l {
3040 + return io.ErrUnexpectedEOF
3041 + }
3042 + b := dAtA[iNdEx]
3043 + iNdEx++
3044 + wire |= uint64(b&0x7F) << shift
3045 + if b < 0x80 {
3046 + break
3047 + }
3048 + }
3049 + fieldNum := int32(wire >> 3)
3050 + wireType := int(wire & 0x7)
3051 + if wireType == 4 {
3052 + return fmt.Errorf("proto: ConnectionResponse: wiretype end group for non-group")
3053 + }
3054 + if fieldNum <= 0 {
3055 + return fmt.Errorf("proto: ConnectionResponse: illegal tag %d (wire type %d)", fieldNum, wire)
3056 + }
3057 + switch fieldNum {
3058 + case 1:
3059 + if wireType != 0 {
3060 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
3061 + }
3062 + m.Code = 0
3063 + for shift := uint(0); ; shift += 7 {
3064 + if shift >= 64 {
3065 + return protohelpers.ErrIntOverflow
3066 + }
3067 + if iNdEx >= l {
3068 + return io.ErrUnexpectedEOF
3069 + }
3070 + b := dAtA[iNdEx]
3071 + iNdEx++
3072 + m.Code |= ResponseCode(b&0x7F) << shift
3073 + if b < 0x80 {
3074 + break
3075 + }
3076 + }
3077 + default:
3078 + iNdEx = preIndex
3079 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3080 + if err != nil {
3081 + return err
3082 + }
3083 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3084 + return protohelpers.ErrInvalidLength
3085 + }
3086 + if (iNdEx + skippy) > l {
3087 + return io.ErrUnexpectedEOF
3088 + }
3089 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3090 + iNdEx += skippy
3091 + }
3092 + }
3093 +
3094 + if iNdEx > l {
3095 + return io.ErrUnexpectedEOF
3096 + }
3097 + return nil
3098 +}
3099 +func (m *Packet) UnmarshalVTUnsafe(dAtA []byte) error {
3100 + l := len(dAtA)
3101 + iNdEx := 0
3102 + for iNdEx < l {
3103 + preIndex := iNdEx
3104 + var wire uint64
3105 + for shift := uint(0); ; shift += 7 {
3106 + if shift >= 64 {
3107 + return protohelpers.ErrIntOverflow
3108 + }
3109 + if iNdEx >= l {
3110 + return io.ErrUnexpectedEOF
3111 + }
3112 + b := dAtA[iNdEx]
3113 + iNdEx++
3114 + wire |= uint64(b&0x7F) << shift
3115 + if b < 0x80 {
3116 + break
3117 + }
3118 + }
3119 + fieldNum := int32(wire >> 3)
3120 + wireType := int(wire & 0x7)
3121 + if wireType == 4 {
3122 + return fmt.Errorf("proto: Packet: wiretype end group for non-group")
3123 + }
3124 + if fieldNum <= 0 {
3125 + return fmt.Errorf("proto: Packet: illegal tag %d (wire type %d)", fieldNum, wire)
3126 + }
3127 + switch fieldNum {
3128 + case 1:
3129 + if wireType != 0 {
3130 + return fmt.Errorf("proto: wrong wireType = %d for field Type", wireType)
3131 + }
3132 + m.Type = 0
3133 + for shift := uint(0); ; shift += 7 {
3134 + if shift >= 64 {
3135 + return protohelpers.ErrIntOverflow
3136 + }
3137 + if iNdEx >= l {
3138 + return io.ErrUnexpectedEOF
3139 + }
3140 + b := dAtA[iNdEx]
3141 + iNdEx++
3142 + m.Type |= PacketType(b&0x7F) << shift
3143 + if b < 0x80 {
3144 + break
3145 + }
3146 + }
3147 + case 2:
3148 + if wireType != 2 {
3149 + return fmt.Errorf("proto: wrong wireType = %d for field Payload", wireType)
3150 + }
3151 + var byteLen int
3152 + for shift := uint(0); ; shift += 7 {
3153 + if shift >= 64 {
3154 + return protohelpers.ErrIntOverflow
3155 + }
3156 + if iNdEx >= l {
3157 + return io.ErrUnexpectedEOF
3158 + }
3159 + b := dAtA[iNdEx]
3160 + iNdEx++
3161 + byteLen |= int(b&0x7F) << shift
3162 + if b < 0x80 {
3163 + break
3164 + }
3165 + }
3166 + if byteLen < 0 {
3167 + return protohelpers.ErrInvalidLength
3168 + }
3169 + postIndex := iNdEx + byteLen
3170 + if postIndex < 0 {
3171 + return protohelpers.ErrInvalidLength
3172 + }
3173 + if postIndex > l {
3174 + return io.ErrUnexpectedEOF
3175 + }
3176 + m.Payload = dAtA[iNdEx:postIndex]
3177 + iNdEx = postIndex
3178 + default:
3179 + iNdEx = preIndex
3180 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3181 + if err != nil {
3182 + return err
3183 + }
3184 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3185 + return protohelpers.ErrInvalidLength
3186 + }
3187 + if (iNdEx + skippy) > l {
3188 + return io.ErrUnexpectedEOF
3189 + }
3190 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3191 + iNdEx += skippy
3192 + }
3193 + }
3194 +
3195 + if iNdEx > l {
3196 + return io.ErrUnexpectedEOF
3197 + }
3198 + return nil
3199 +}
3200 +func (m *RelayInfo) UnmarshalVTUnsafe(dAtA []byte) error {
3201 + l := len(dAtA)
3202 + iNdEx := 0
3203 + for iNdEx < l {
3204 + preIndex := iNdEx
3205 + var wire uint64
3206 + for shift := uint(0); ; shift += 7 {
3207 + if shift >= 64 {
3208 + return protohelpers.ErrIntOverflow
3209 + }
3210 + if iNdEx >= l {
3211 + return io.ErrUnexpectedEOF
3212 + }
3213 + b := dAtA[iNdEx]
3214 + iNdEx++
3215 + wire |= uint64(b&0x7F) << shift
3216 + if b < 0x80 {
3217 + break
3218 + }
3219 + }
3220 + fieldNum := int32(wire >> 3)
3221 + wireType := int(wire & 0x7)
3222 + if wireType == 4 {
3223 + return fmt.Errorf("proto: RelayInfo: wiretype end group for non-group")
3224 + }
3225 + if fieldNum <= 0 {
3226 + return fmt.Errorf("proto: RelayInfo: illegal tag %d (wire type %d)", fieldNum, wire)
3227 + }
3228 + switch fieldNum {
3229 + case 1:
3230 + if wireType != 2 {
3231 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
3232 + }
3233 + var msglen int
3234 + for shift := uint(0); ; shift += 7 {
3235 + if shift >= 64 {
3236 + return protohelpers.ErrIntOverflow
3237 + }
3238 + if iNdEx >= l {
3239 + return io.ErrUnexpectedEOF
3240 + }
3241 + b := dAtA[iNdEx]
3242 + iNdEx++
3243 + msglen |= int(b&0x7F) << shift
3244 + if b < 0x80 {
3245 + break
3246 + }
3247 + }
3248 + if msglen < 0 {
3249 + return protohelpers.ErrInvalidLength
3250 + }
3251 + postIndex := iNdEx + msglen
3252 + if postIndex < 0 {
3253 + return protohelpers.ErrInvalidLength
3254 + }
3255 + if postIndex > l {
3256 + return io.ErrUnexpectedEOF
3257 + }
3258 + if m.Identity == nil {
3259 + m.Identity = &rdsec.Identity{}
3260 + }
3261 + if unmarshal, ok := interface{}(m.Identity).(interface {
3262 + UnmarshalVTUnsafe([]byte) error
3263 + }); ok {
3264 + if err := unmarshal.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3265 + return err
3266 + }
3267 + } else {
3268 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
3269 + return err
3270 + }
3271 + }
3272 + iNdEx = postIndex
3273 + case 2:
3274 + if wireType != 2 {
3275 + return fmt.Errorf("proto: wrong wireType = %d for field Address", wireType)
3276 + }
3277 + var stringLen uint64
3278 + for shift := uint(0); ; shift += 7 {
3279 + if shift >= 64 {
3280 + return protohelpers.ErrIntOverflow
3281 + }
3282 + if iNdEx >= l {
3283 + return io.ErrUnexpectedEOF
3284 + }
3285 + b := dAtA[iNdEx]
3286 + iNdEx++
3287 + stringLen |= uint64(b&0x7F) << shift
3288 + if b < 0x80 {
3289 + break
3290 + }
3291 + }
3292 + intStringLen := int(stringLen)
3293 + if intStringLen < 0 {
3294 + return protohelpers.ErrInvalidLength
3295 + }
3296 + postIndex := iNdEx + intStringLen
3297 + if postIndex < 0 {
3298 + return protohelpers.ErrInvalidLength
3299 + }
3300 + if postIndex > l {
3301 + return io.ErrUnexpectedEOF
3302 + }
3303 + var stringValue string
3304 + if intStringLen > 0 {
3305 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
3306 + }
3307 + m.Address = append(m.Address, stringValue)
3308 + iNdEx = postIndex
3309 + case 3:
3310 + if wireType != 2 {
3311 + return fmt.Errorf("proto: wrong wireType = %d for field Leases", wireType)
3312 + }
3313 + var stringLen uint64
3314 + for shift := uint(0); ; shift += 7 {
3315 + if shift >= 64 {
3316 + return protohelpers.ErrIntOverflow
3317 + }
3318 + if iNdEx >= l {
3319 + return io.ErrUnexpectedEOF
3320 + }
3321 + b := dAtA[iNdEx]
3322 + iNdEx++
3323 + stringLen |= uint64(b&0x7F) << shift
3324 + if b < 0x80 {
3325 + break
3326 + }
3327 + }
3328 + intStringLen := int(stringLen)
3329 + if intStringLen < 0 {
3330 + return protohelpers.ErrInvalidLength
3331 + }
3332 + postIndex := iNdEx + intStringLen
3333 + if postIndex < 0 {
3334 + return protohelpers.ErrInvalidLength
3335 + }
3336 + if postIndex > l {
3337 + return io.ErrUnexpectedEOF
3338 + }
3339 + var stringValue string
3340 + if intStringLen > 0 {
3341 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
3342 + }
3343 + m.Leases = append(m.Leases, stringValue)
3344 + iNdEx = postIndex
3345 + default:
3346 + iNdEx = preIndex
3347 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3348 + if err != nil {
3349 + return err
3350 + }
3351 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3352 + return protohelpers.ErrInvalidLength
3353 + }
3354 + if (iNdEx + skippy) > l {
3355 + return io.ErrUnexpectedEOF
3356 + }
3357 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3358 + iNdEx += skippy
3359 + }
3360 + }
3361 +
3362 + if iNdEx > l {
3363 + return io.ErrUnexpectedEOF
3364 + }
3365 + return nil
3366 +}
3367 +func (m *RelayInfoRequest) UnmarshalVTUnsafe(dAtA []byte) error {
3368 + l := len(dAtA)
3369 + iNdEx := 0
3370 + for iNdEx < l {
3371 + preIndex := iNdEx
3372 + var wire uint64
3373 + for shift := uint(0); ; shift += 7 {
3374 + if shift >= 64 {
3375 + return protohelpers.ErrIntOverflow
3376 + }
3377 + if iNdEx >= l {
3378 + return io.ErrUnexpectedEOF
3379 + }
3380 + b := dAtA[iNdEx]
3381 + iNdEx++
3382 + wire |= uint64(b&0x7F) << shift
3383 + if b < 0x80 {
3384 + break
3385 + }
3386 + }
3387 + fieldNum := int32(wire >> 3)
3388 + wireType := int(wire & 0x7)
3389 + if wireType == 4 {
3390 + return fmt.Errorf("proto: RelayInfoRequest: wiretype end group for non-group")
3391 + }
3392 + if fieldNum <= 0 {
3393 + return fmt.Errorf("proto: RelayInfoRequest: illegal tag %d (wire type %d)", fieldNum, wire)
3394 + }
3395 + switch fieldNum {
3396 + default:
3397 + iNdEx = preIndex
3398 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3399 + if err != nil {
3400 + return err
3401 + }
3402 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3403 + return protohelpers.ErrInvalidLength
3404 + }
3405 + if (iNdEx + skippy) > l {
3406 + return io.ErrUnexpectedEOF
3407 + }
3408 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3409 + iNdEx += skippy
3410 + }
3411 + }
3412 +
3413 + if iNdEx > l {
3414 + return io.ErrUnexpectedEOF
3415 + }
3416 + return nil
3417 +}
3418 +func (m *RelayInfoResponse) UnmarshalVTUnsafe(dAtA []byte) error {
3419 + l := len(dAtA)
3420 + iNdEx := 0
3421 + for iNdEx < l {
3422 + preIndex := iNdEx
3423 + var wire uint64
3424 + for shift := uint(0); ; shift += 7 {
3425 + if shift >= 64 {
3426 + return protohelpers.ErrIntOverflow
3427 + }
3428 + if iNdEx >= l {
3429 + return io.ErrUnexpectedEOF
3430 + }
3431 + b := dAtA[iNdEx]
3432 + iNdEx++
3433 + wire |= uint64(b&0x7F) << shift
3434 + if b < 0x80 {
3435 + break
3436 + }
3437 + }
3438 + fieldNum := int32(wire >> 3)
3439 + wireType := int(wire & 0x7)
3440 + if wireType == 4 {
3441 + return fmt.Errorf("proto: RelayInfoResponse: wiretype end group for non-group")
3442 + }
3443 + if fieldNum <= 0 {
3444 + return fmt.Errorf("proto: RelayInfoResponse: illegal tag %d (wire type %d)", fieldNum, wire)
3445 + }
3446 + switch fieldNum {
3447 + case 1:
3448 + if wireType != 2 {
3449 + return fmt.Errorf("proto: wrong wireType = %d for field RelayInfo", wireType)
3450 + }
3451 + var msglen int
3452 + for shift := uint(0); ; shift += 7 {
3453 + if shift >= 64 {
3454 + return protohelpers.ErrIntOverflow
3455 + }
3456 + if iNdEx >= l {
3457 + return io.ErrUnexpectedEOF
3458 + }
3459 + b := dAtA[iNdEx]
3460 + iNdEx++
3461 + msglen |= int(b&0x7F) << shift
3462 + if b < 0x80 {
3463 + break
3464 + }
3465 + }
3466 + if msglen < 0 {
3467 + return protohelpers.ErrInvalidLength
3468 + }
3469 + postIndex := iNdEx + msglen
3470 + if postIndex < 0 {
3471 + return protohelpers.ErrInvalidLength
3472 + }
3473 + if postIndex > l {
3474 + return io.ErrUnexpectedEOF
3475 + }
3476 + if m.RelayInfo == nil {
3477 + m.RelayInfo = &RelayInfo{}
3478 + }
3479 + if err := m.RelayInfo.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3480 + return err
3481 + }
3482 + iNdEx = postIndex
3483 + default:
3484 + iNdEx = preIndex
3485 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3486 + if err != nil {
3487 + return err
3488 + }
3489 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3490 + return protohelpers.ErrInvalidLength
3491 + }
3492 + if (iNdEx + skippy) > l {
3493 + return io.ErrUnexpectedEOF
3494 + }
3495 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3496 + iNdEx += skippy
3497 + }
3498 + }
3499 +
3500 + if iNdEx > l {
3501 + return io.ErrUnexpectedEOF
3502 + }
3503 + return nil
3504 +}
3505 +func (m *Lease) UnmarshalVTUnsafe(dAtA []byte) error {
3506 + l := len(dAtA)
3507 + iNdEx := 0
3508 + for iNdEx < l {
3509 + preIndex := iNdEx
3510 + var wire uint64
3511 + for shift := uint(0); ; shift += 7 {
3512 + if shift >= 64 {
3513 + return protohelpers.ErrIntOverflow
3514 + }
3515 + if iNdEx >= l {
3516 + return io.ErrUnexpectedEOF
3517 + }
3518 + b := dAtA[iNdEx]
3519 + iNdEx++
3520 + wire |= uint64(b&0x7F) << shift
3521 + if b < 0x80 {
3522 + break
3523 + }
3524 + }
3525 + fieldNum := int32(wire >> 3)
3526 + wireType := int(wire & 0x7)
3527 + if wireType == 4 {
3528 + return fmt.Errorf("proto: Lease: wiretype end group for non-group")
3529 + }
3530 + if fieldNum <= 0 {
3531 + return fmt.Errorf("proto: Lease: illegal tag %d (wire type %d)", fieldNum, wire)
3532 + }
3533 + switch fieldNum {
3534 + case 1:
3535 + if wireType != 2 {
3536 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
3537 + }
3538 + var msglen int
3539 + for shift := uint(0); ; shift += 7 {
3540 + if shift >= 64 {
3541 + return protohelpers.ErrIntOverflow
3542 + }
3543 + if iNdEx >= l {
3544 + return io.ErrUnexpectedEOF
3545 + }
3546 + b := dAtA[iNdEx]
3547 + iNdEx++
3548 + msglen |= int(b&0x7F) << shift
3549 + if b < 0x80 {
3550 + break
3551 + }
3552 + }
3553 + if msglen < 0 {
3554 + return protohelpers.ErrInvalidLength
3555 + }
3556 + postIndex := iNdEx + msglen
3557 + if postIndex < 0 {
3558 + return protohelpers.ErrInvalidLength
3559 + }
3560 + if postIndex > l {
3561 + return io.ErrUnexpectedEOF
3562 + }
3563 + if m.Identity == nil {
3564 + m.Identity = &rdsec.Identity{}
3565 + }
3566 + if unmarshal, ok := interface{}(m.Identity).(interface {
3567 + UnmarshalVTUnsafe([]byte) error
3568 + }); ok {
3569 + if err := unmarshal.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3570 + return err
3571 + }
3572 + } else {
3573 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
3574 + return err
3575 + }
3576 + }
3577 + iNdEx = postIndex
3578 + case 2:
3579 + if wireType != 0 {
3580 + return fmt.Errorf("proto: wrong wireType = %d for field Expires", wireType)
3581 + }
3582 + m.Expires = 0
3583 + for shift := uint(0); ; shift += 7 {
3584 + if shift >= 64 {
3585 + return protohelpers.ErrIntOverflow
3586 + }
3587 + if iNdEx >= l {
3588 + return io.ErrUnexpectedEOF
3589 + }
3590 + b := dAtA[iNdEx]
3591 + iNdEx++
3592 + m.Expires |= int64(b&0x7F) << shift
3593 + if b < 0x80 {
3594 + break
3595 + }
3596 + }
3597 + case 3:
3598 + if wireType != 2 {
3599 + return fmt.Errorf("proto: wrong wireType = %d for field Name", wireType)
3600 + }
3601 + var stringLen uint64
3602 + for shift := uint(0); ; shift += 7 {
3603 + if shift >= 64 {
3604 + return protohelpers.ErrIntOverflow
3605 + }
3606 + if iNdEx >= l {
3607 + return io.ErrUnexpectedEOF
3608 + }
3609 + b := dAtA[iNdEx]
3610 + iNdEx++
3611 + stringLen |= uint64(b&0x7F) << shift
3612 + if b < 0x80 {
3613 + break
3614 + }
3615 + }
3616 + intStringLen := int(stringLen)
3617 + if intStringLen < 0 {
3618 + return protohelpers.ErrInvalidLength
3619 + }
3620 + postIndex := iNdEx + intStringLen
3621 + if postIndex < 0 {
3622 + return protohelpers.ErrInvalidLength
3623 + }
3624 + if postIndex > l {
3625 + return io.ErrUnexpectedEOF
3626 + }
3627 + var stringValue string
3628 + if intStringLen > 0 {
3629 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
3630 + }
3631 + m.Name = stringValue
3632 + iNdEx = postIndex
3633 + case 4:
3634 + if wireType != 2 {
3635 + return fmt.Errorf("proto: wrong wireType = %d for field Alpn", wireType)
3636 + }
3637 + var stringLen uint64
3638 + for shift := uint(0); ; shift += 7 {
3639 + if shift >= 64 {
3640 + return protohelpers.ErrIntOverflow
3641 + }
3642 + if iNdEx >= l {
3643 + return io.ErrUnexpectedEOF
3644 + }
3645 + b := dAtA[iNdEx]
3646 + iNdEx++
3647 + stringLen |= uint64(b&0x7F) << shift
3648 + if b < 0x80 {
3649 + break
3650 + }
3651 + }
3652 + intStringLen := int(stringLen)
3653 + if intStringLen < 0 {
3654 + return protohelpers.ErrInvalidLength
3655 + }
3656 + postIndex := iNdEx + intStringLen
3657 + if postIndex < 0 {
3658 + return protohelpers.ErrInvalidLength
3659 + }
3660 + if postIndex > l {
3661 + return io.ErrUnexpectedEOF
3662 + }
3663 + var stringValue string
3664 + if intStringLen > 0 {
3665 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
3666 + }
3667 + m.Alpn = append(m.Alpn, stringValue)
3668 + iNdEx = postIndex
3669 + default:
3670 + iNdEx = preIndex
3671 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3672 + if err != nil {
3673 + return err
3674 + }
3675 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3676 + return protohelpers.ErrInvalidLength
3677 + }
3678 + if (iNdEx + skippy) > l {
3679 + return io.ErrUnexpectedEOF
3680 + }
3681 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3682 + iNdEx += skippy
3683 + }
3684 + }
3685 +
3686 + if iNdEx > l {
3687 + return io.ErrUnexpectedEOF
3688 + }
3689 + return nil
3690 +}
3691 +func (m *LeaseUpdateRequest) UnmarshalVTUnsafe(dAtA []byte) error {
3692 + l := len(dAtA)
3693 + iNdEx := 0
3694 + for iNdEx < l {
3695 + preIndex := iNdEx
3696 + var wire uint64
3697 + for shift := uint(0); ; shift += 7 {
3698 + if shift >= 64 {
3699 + return protohelpers.ErrIntOverflow
3700 + }
3701 + if iNdEx >= l {
3702 + return io.ErrUnexpectedEOF
3703 + }
3704 + b := dAtA[iNdEx]
3705 + iNdEx++
3706 + wire |= uint64(b&0x7F) << shift
3707 + if b < 0x80 {
3708 + break
3709 + }
3710 + }
3711 + fieldNum := int32(wire >> 3)
3712 + wireType := int(wire & 0x7)
3713 + if wireType == 4 {
3714 + return fmt.Errorf("proto: LeaseUpdateRequest: wiretype end group for non-group")
3715 + }
3716 + if fieldNum <= 0 {
3717 + return fmt.Errorf("proto: LeaseUpdateRequest: illegal tag %d (wire type %d)", fieldNum, wire)
3718 + }
3719 + switch fieldNum {
3720 + case 1:
3721 + if wireType != 2 {
3722 + return fmt.Errorf("proto: wrong wireType = %d for field Lease", wireType)
3723 + }
3724 + var msglen int
3725 + for shift := uint(0); ; shift += 7 {
3726 + if shift >= 64 {
3727 + return protohelpers.ErrIntOverflow
3728 + }
3729 + if iNdEx >= l {
3730 + return io.ErrUnexpectedEOF
3731 + }
3732 + b := dAtA[iNdEx]
3733 + iNdEx++
3734 + msglen |= int(b&0x7F) << shift
3735 + if b < 0x80 {
3736 + break
3737 + }
3738 + }
3739 + if msglen < 0 {
3740 + return protohelpers.ErrInvalidLength
3741 + }
3742 + postIndex := iNdEx + msglen
3743 + if postIndex < 0 {
3744 + return protohelpers.ErrInvalidLength
3745 + }
3746 + if postIndex > l {
3747 + return io.ErrUnexpectedEOF
3748 + }
3749 + if m.Lease == nil {
3750 + m.Lease = &Lease{}
3751 + }
3752 + if err := m.Lease.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3753 + return err
3754 + }
3755 + iNdEx = postIndex
3756 + case 2:
3757 + if wireType != 2 {
3758 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
3759 + }
3760 + var byteLen int
3761 + for shift := uint(0); ; shift += 7 {
3762 + if shift >= 64 {
3763 + return protohelpers.ErrIntOverflow
3764 + }
3765 + if iNdEx >= l {
3766 + return io.ErrUnexpectedEOF
3767 + }
3768 + b := dAtA[iNdEx]
3769 + iNdEx++
3770 + byteLen |= int(b&0x7F) << shift
3771 + if b < 0x80 {
3772 + break
3773 + }
3774 + }
3775 + if byteLen < 0 {
3776 + return protohelpers.ErrInvalidLength
3777 + }
3778 + postIndex := iNdEx + byteLen
3779 + if postIndex < 0 {
3780 + return protohelpers.ErrInvalidLength
3781 + }
3782 + if postIndex > l {
3783 + return io.ErrUnexpectedEOF
3784 + }
3785 + m.Nonce = dAtA[iNdEx:postIndex]
3786 + iNdEx = postIndex
3787 + case 3:
3788 + if wireType != 0 {
3789 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
3790 + }
3791 + m.Timestamp = 0
3792 + for shift := uint(0); ; shift += 7 {
3793 + if shift >= 64 {
3794 + return protohelpers.ErrIntOverflow
3795 + }
3796 + if iNdEx >= l {
3797 + return io.ErrUnexpectedEOF
3798 + }
3799 + b := dAtA[iNdEx]
3800 + iNdEx++
3801 + m.Timestamp |= int64(b&0x7F) << shift
3802 + if b < 0x80 {
3803 + break
3804 + }
3805 + }
3806 + default:
3807 + iNdEx = preIndex
3808 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3809 + if err != nil {
3810 + return err
3811 + }
3812 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3813 + return protohelpers.ErrInvalidLength
3814 + }
3815 + if (iNdEx + skippy) > l {
3816 + return io.ErrUnexpectedEOF
3817 + }
3818 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3819 + iNdEx += skippy
3820 + }
3821 + }
3822 +
3823 + if iNdEx > l {
3824 + return io.ErrUnexpectedEOF
3825 + }
3826 + return nil
3827 +}
3828 +func (m *LeaseUpdateResponse) UnmarshalVTUnsafe(dAtA []byte) error {
3829 + l := len(dAtA)
3830 + iNdEx := 0
3831 + for iNdEx < l {
3832 + preIndex := iNdEx
3833 + var wire uint64
3834 + for shift := uint(0); ; shift += 7 {
3835 + if shift >= 64 {
3836 + return protohelpers.ErrIntOverflow
3837 + }
3838 + if iNdEx >= l {
3839 + return io.ErrUnexpectedEOF
3840 + }
3841 + b := dAtA[iNdEx]
3842 + iNdEx++
3843 + wire |= uint64(b&0x7F) << shift
3844 + if b < 0x80 {
3845 + break
3846 + }
3847 + }
3848 + fieldNum := int32(wire >> 3)
3849 + wireType := int(wire & 0x7)
3850 + if wireType == 4 {
3851 + return fmt.Errorf("proto: LeaseUpdateResponse: wiretype end group for non-group")
3852 + }
3853 + if fieldNum <= 0 {
3854 + return fmt.Errorf("proto: LeaseUpdateResponse: illegal tag %d (wire type %d)", fieldNum, wire)
3855 + }
3856 + switch fieldNum {
3857 + case 1:
3858 + if wireType != 0 {
3859 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
3860 + }
3861 + m.Code = 0
3862 + for shift := uint(0); ; shift += 7 {
3863 + if shift >= 64 {
3864 + return protohelpers.ErrIntOverflow
3865 + }
3866 + if iNdEx >= l {
3867 + return io.ErrUnexpectedEOF
3868 + }
3869 + b := dAtA[iNdEx]
3870 + iNdEx++
3871 + m.Code |= ResponseCode(b&0x7F) << shift
3872 + if b < 0x80 {
3873 + break
3874 + }
3875 + }
3876 + default:
3877 + iNdEx = preIndex
3878 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
3879 + if err != nil {
3880 + return err
3881 + }
3882 + if (skippy < 0) || (iNdEx+skippy) < 0 {
3883 + return protohelpers.ErrInvalidLength
3884 + }
3885 + if (iNdEx + skippy) > l {
3886 + return io.ErrUnexpectedEOF
3887 + }
3888 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
3889 + iNdEx += skippy
3890 + }
3891 + }
3892 +
3893 + if iNdEx > l {
3894 + return io.ErrUnexpectedEOF
3895 + }
3896 + return nil
3897 +}
3898 +func (m *LeaseDeleteRequest) UnmarshalVTUnsafe(dAtA []byte) error {
3899 + l := len(dAtA)
3900 + iNdEx := 0
3901 + for iNdEx < l {
3902 + preIndex := iNdEx
3903 + var wire uint64
3904 + for shift := uint(0); ; shift += 7 {
3905 + if shift >= 64 {
3906 + return protohelpers.ErrIntOverflow
3907 + }
3908 + if iNdEx >= l {
3909 + return io.ErrUnexpectedEOF
3910 + }
3911 + b := dAtA[iNdEx]
3912 + iNdEx++
3913 + wire |= uint64(b&0x7F) << shift
3914 + if b < 0x80 {
3915 + break
3916 + }
3917 + }
3918 + fieldNum := int32(wire >> 3)
3919 + wireType := int(wire & 0x7)
3920 + if wireType == 4 {
3921 + return fmt.Errorf("proto: LeaseDeleteRequest: wiretype end group for non-group")
3922 + }
3923 + if fieldNum <= 0 {
3924 + return fmt.Errorf("proto: LeaseDeleteRequest: illegal tag %d (wire type %d)", fieldNum, wire)
3925 + }
3926 + switch fieldNum {
3927 + case 1:
3928 + if wireType != 2 {
3929 + return fmt.Errorf("proto: wrong wireType = %d for field Identity", wireType)
3930 + }
3931 + var msglen int
3932 + for shift := uint(0); ; shift += 7 {
3933 + if shift >= 64 {
3934 + return protohelpers.ErrIntOverflow
3935 + }
3936 + if iNdEx >= l {
3937 + return io.ErrUnexpectedEOF
3938 + }
3939 + b := dAtA[iNdEx]
3940 + iNdEx++
3941 + msglen |= int(b&0x7F) << shift
3942 + if b < 0x80 {
3943 + break
3944 + }
3945 + }
3946 + if msglen < 0 {
3947 + return protohelpers.ErrInvalidLength
3948 + }
3949 + postIndex := iNdEx + msglen
3950 + if postIndex < 0 {
3951 + return protohelpers.ErrInvalidLength
3952 + }
3953 + if postIndex > l {
3954 + return io.ErrUnexpectedEOF
3955 + }
3956 + if m.Identity == nil {
3957 + m.Identity = &rdsec.Identity{}
3958 + }
3959 + if unmarshal, ok := interface{}(m.Identity).(interface {
3960 + UnmarshalVTUnsafe([]byte) error
3961 + }); ok {
3962 + if err := unmarshal.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3963 + return err
3964 + }
3965 + } else {
3966 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.Identity); err != nil {
3967 + return err
3968 + }
3969 + }
3970 + iNdEx = postIndex
3971 + case 2:
3972 + if wireType != 2 {
3973 + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType)
3974 + }
3975 + var byteLen int
3976 + for shift := uint(0); ; shift += 7 {
3977 + if shift >= 64 {
3978 + return protohelpers.ErrIntOverflow
3979 + }
3980 + if iNdEx >= l {
3981 + return io.ErrUnexpectedEOF
3982 + }
3983 + b := dAtA[iNdEx]
3984 + iNdEx++
3985 + byteLen |= int(b&0x7F) << shift
3986 + if b < 0x80 {
3987 + break
3988 + }
3989 + }
3990 + if byteLen < 0 {
3991 + return protohelpers.ErrInvalidLength
3992 + }
3993 + postIndex := iNdEx + byteLen
3994 + if postIndex < 0 {
3995 + return protohelpers.ErrInvalidLength
3996 + }
3997 + if postIndex > l {
3998 + return io.ErrUnexpectedEOF
3999 + }
4000 + m.Nonce = dAtA[iNdEx:postIndex]
4001 + iNdEx = postIndex
4002 + case 3:
4003 + if wireType != 0 {
4004 + return fmt.Errorf("proto: wrong wireType = %d for field Timestamp", wireType)
4005 + }
4006 + m.Timestamp = 0
4007 + for shift := uint(0); ; shift += 7 {
4008 + if shift >= 64 {
4009 + return protohelpers.ErrIntOverflow
4010 + }
4011 + if iNdEx >= l {
4012 + return io.ErrUnexpectedEOF
4013 + }
4014 + b := dAtA[iNdEx]
4015 + iNdEx++
4016 + m.Timestamp |= int64(b&0x7F) << shift
4017 + if b < 0x80 {
4018 + break
4019 + }
4020 + }
4021 + default:
4022 + iNdEx = preIndex
4023 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
4024 + if err != nil {
4025 + return err
4026 + }
4027 + if (skippy < 0) || (iNdEx+skippy) < 0 {
4028 + return protohelpers.ErrInvalidLength
4029 + }
4030 + if (iNdEx + skippy) > l {
4031 + return io.ErrUnexpectedEOF
4032 + }
4033 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
4034 + iNdEx += skippy
4035 + }
4036 + }
4037 +
4038 + if iNdEx > l {
4039 + return io.ErrUnexpectedEOF
4040 + }
4041 + return nil
4042 +}
4043 +func (m *LeaseDeleteResponse) UnmarshalVTUnsafe(dAtA []byte) error {
4044 + l := len(dAtA)
4045 + iNdEx := 0
4046 + for iNdEx < l {
4047 + preIndex := iNdEx
4048 + var wire uint64
4049 + for shift := uint(0); ; shift += 7 {
4050 + if shift >= 64 {
4051 + return protohelpers.ErrIntOverflow
4052 + }
4053 + if iNdEx >= l {
4054 + return io.ErrUnexpectedEOF
4055 + }
4056 + b := dAtA[iNdEx]
4057 + iNdEx++
4058 + wire |= uint64(b&0x7F) << shift
4059 + if b < 0x80 {
4060 + break
4061 + }
4062 + }
4063 + fieldNum := int32(wire >> 3)
4064 + wireType := int(wire & 0x7)
4065 + if wireType == 4 {
4066 + return fmt.Errorf("proto: LeaseDeleteResponse: wiretype end group for non-group")
4067 + }
4068 + if fieldNum <= 0 {
4069 + return fmt.Errorf("proto: LeaseDeleteResponse: illegal tag %d (wire type %d)", fieldNum, wire)
4070 + }
4071 + switch fieldNum {
4072 + case 1:
4073 + if wireType != 0 {
4074 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
4075 + }
4076 + m.Code = 0
4077 + for shift := uint(0); ; shift += 7 {
4078 + if shift >= 64 {
4079 + return protohelpers.ErrIntOverflow
4080 + }
4081 + if iNdEx >= l {
4082 + return io.ErrUnexpectedEOF
4083 + }
4084 + b := dAtA[iNdEx]
4085 + iNdEx++
4086 + m.Code |= ResponseCode(b&0x7F) << shift
4087 + if b < 0x80 {
4088 + break
4089 + }
4090 + }
4091 + default:
4092 + iNdEx = preIndex
4093 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
4094 + if err != nil {
4095 + return err
4096 + }
4097 + if (skippy < 0) || (iNdEx+skippy) < 0 {
4098 + return protohelpers.ErrInvalidLength
4099 + }
4100 + if (iNdEx + skippy) > l {
4101 + return io.ErrUnexpectedEOF
4102 + }
4103 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
4104 + iNdEx += skippy
4105 + }
4106 + }
4107 +
4108 + if iNdEx > l {
4109 + return io.ErrUnexpectedEOF
4110 + }
4111 + return nil
4112 +}
4113 +func (m *ConnectionRequest) UnmarshalVTUnsafe(dAtA []byte) error {
4114 + l := len(dAtA)
4115 + iNdEx := 0
4116 + for iNdEx < l {
4117 + preIndex := iNdEx
4118 + var wire uint64
4119 + for shift := uint(0); ; shift += 7 {
4120 + if shift >= 64 {
4121 + return protohelpers.ErrIntOverflow
4122 + }
4123 + if iNdEx >= l {
4124 + return io.ErrUnexpectedEOF
4125 + }
4126 + b := dAtA[iNdEx]
4127 + iNdEx++
4128 + wire |= uint64(b&0x7F) << shift
4129 + if b < 0x80 {
4130 + break
4131 + }
4132 + }
4133 + fieldNum := int32(wire >> 3)
4134 + wireType := int(wire & 0x7)
4135 + if wireType == 4 {
4136 + return fmt.Errorf("proto: ConnectionRequest: wiretype end group for non-group")
4137 + }
4138 + if fieldNum <= 0 {
4139 + return fmt.Errorf("proto: ConnectionRequest: illegal tag %d (wire type %d)", fieldNum, wire)
4140 + }
4141 + switch fieldNum {
4142 + case 1:
4143 + if wireType != 2 {
4144 + return fmt.Errorf("proto: wrong wireType = %d for field LeaseId", wireType)
4145 + }
4146 + var stringLen uint64
4147 + for shift := uint(0); ; shift += 7 {
4148 + if shift >= 64 {
4149 + return protohelpers.ErrIntOverflow
4150 + }
4151 + if iNdEx >= l {
4152 + return io.ErrUnexpectedEOF
4153 + }
4154 + b := dAtA[iNdEx]
4155 + iNdEx++
4156 + stringLen |= uint64(b&0x7F) << shift
4157 + if b < 0x80 {
4158 + break
4159 + }
4160 + }
4161 + intStringLen := int(stringLen)
4162 + if intStringLen < 0 {
4163 + return protohelpers.ErrInvalidLength
4164 + }
4165 + postIndex := iNdEx + intStringLen
4166 + if postIndex < 0 {
4167 + return protohelpers.ErrInvalidLength
4168 + }
4169 + if postIndex > l {
4170 + return io.ErrUnexpectedEOF
4171 + }
4172 + var stringValue string
4173 + if intStringLen > 0 {
4174 + stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
4175 + }
4176 + m.LeaseId = stringValue
4177 + iNdEx = postIndex
4178 + case 2:
4179 + if wireType != 2 {
4180 + return fmt.Errorf("proto: wrong wireType = %d for field ClientIdentity", wireType)
4181 + }
4182 + var msglen int
4183 + for shift := uint(0); ; shift += 7 {
4184 + if shift >= 64 {
4185 + return protohelpers.ErrIntOverflow
4186 + }
4187 + if iNdEx >= l {
4188 + return io.ErrUnexpectedEOF
4189 + }
4190 + b := dAtA[iNdEx]
4191 + iNdEx++
4192 + msglen |= int(b&0x7F) << shift
4193 + if b < 0x80 {
4194 + break
4195 + }
4196 + }
4197 + if msglen < 0 {
4198 + return protohelpers.ErrInvalidLength
4199 + }
4200 + postIndex := iNdEx + msglen
4201 + if postIndex < 0 {
4202 + return protohelpers.ErrInvalidLength
4203 + }
4204 + if postIndex > l {
4205 + return io.ErrUnexpectedEOF
4206 + }
4207 + if m.ClientIdentity == nil {
4208 + m.ClientIdentity = &rdsec.Identity{}
4209 + }
4210 + if unmarshal, ok := interface{}(m.ClientIdentity).(interface {
4211 + UnmarshalVTUnsafe([]byte) error
4212 + }); ok {
4213 + if err := unmarshal.UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
4214 + return err
4215 + }
4216 + } else {
4217 + if err := proto.Unmarshal(dAtA[iNdEx:postIndex], m.ClientIdentity); err != nil {
4218 + return err
4219 + }
4220 + }
4221 + iNdEx = postIndex
4222 + default:
4223 + iNdEx = preIndex
4224 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
4225 + if err != nil {
4226 + return err
4227 + }
4228 + if (skippy < 0) || (iNdEx+skippy) < 0 {
4229 + return protohelpers.ErrInvalidLength
4230 + }
4231 + if (iNdEx + skippy) > l {
4232 + return io.ErrUnexpectedEOF
4233 + }
4234 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
4235 + iNdEx += skippy
4236 + }
4237 + }
4238 +
4239 + if iNdEx > l {
4240 + return io.ErrUnexpectedEOF
4241 + }
4242 + return nil
4243 +}
4244 +func (m *ConnectionResponse) UnmarshalVTUnsafe(dAtA []byte) error {
4245 + l := len(dAtA)
4246 + iNdEx := 0
4247 + for iNdEx < l {
4248 + preIndex := iNdEx
4249 + var wire uint64
4250 + for shift := uint(0); ; shift += 7 {
4251 + if shift >= 64 {
4252 + return protohelpers.ErrIntOverflow
4253 + }
4254 + if iNdEx >= l {
4255 + return io.ErrUnexpectedEOF
4256 + }
4257 + b := dAtA[iNdEx]
4258 + iNdEx++
4259 + wire |= uint64(b&0x7F) << shift
4260 + if b < 0x80 {
4261 + break
4262 + }
4263 + }
4264 + fieldNum := int32(wire >> 3)
4265 + wireType := int(wire & 0x7)
4266 + if wireType == 4 {
4267 + return fmt.Errorf("proto: ConnectionResponse: wiretype end group for non-group")
4268 + }
4269 + if fieldNum <= 0 {
4270 + return fmt.Errorf("proto: ConnectionResponse: illegal tag %d (wire type %d)", fieldNum, wire)
4271 + }
4272 + switch fieldNum {
4273 + case 1:
4274 + if wireType != 0 {
4275 + return fmt.Errorf("proto: wrong wireType = %d for field Code", wireType)
4276 + }
4277 + m.Code = 0
4278 + for shift := uint(0); ; shift += 7 {
4279 + if shift >= 64 {
4280 + return protohelpers.ErrIntOverflow
4281 + }
4282 + if iNdEx >= l {
4283 + return io.ErrUnexpectedEOF
4284 + }
4285 + b := dAtA[iNdEx]
4286 + iNdEx++
4287 + m.Code |= ResponseCode(b&0x7F) << shift
4288 + if b < 0x80 {
4289 + break
4290 + }
4291 + }
4292 + default:
4293 + iNdEx = preIndex
4294 + skippy, err := protohelpers.Skip(dAtA[iNdEx:])
4295 + if err != nil {
4296 + return err
4297 + }
4298 + if (skippy < 0) || (iNdEx+skippy) < 0 {
4299 + return protohelpers.ErrInvalidLength
4300 + }
4301 + if (iNdEx + skippy) > l {
4302 + return io.ErrUnexpectedEOF
4303 + }
4304 + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...)
4305 + iNdEx += skippy
4306 + }
4307 + }
4308 +
4309 + if iNdEx > l {
4310 + return io.ErrUnexpectedEOF
4311 + }
4312 + return nil
4313 +}
relaydns/handlers.go new
+334
@@ -0,0 +1,334 @@
1 +package relaydns
2 +
3 +import (
4 + "encoding/binary"
5 + "io"
6 + "sync"
7 +
8 + "github.com/gosuda/relaydns/relaydns/core/cryptoops"
9 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
10 + "github.com/gosuda/relaydns/relaydns/core/proto/rdverb"
11 + "github.com/hashicorp/yamux"
12 + "github.com/valyala/bytebufferpool"
13 +)
14 +
15 +type StreamContext struct {
16 + Server *RelayServer
17 + Stream *yamux.Stream
18 + Connection *Connection
19 + ConnectionID int64
20 + Hijacked *bool
21 +}
22 +
23 +func (ctx *StreamContext) Hijack() {
24 + *ctx.Hijacked = true
25 +}
26 +
27 +func (g *RelayServer) handleRelayInfoRequest(ctx *StreamContext, packet *rdverb.Packet) error {
28 + _, err := decodeProtobuf[*rdverb.RelayInfoRequest](packet.Payload)
29 + if err != nil {
30 + return err
31 + }
32 +
33 + var resp rdverb.RelayInfoResponse
34 + resp.RelayInfo = g.relayInfo()
35 + response, err := resp.MarshalVT()
36 + if err != nil {
37 + return err
38 + }
39 +
40 + return writePacket(ctx.Stream, &rdverb.Packet{
41 + Type: rdverb.PacketType_PACKET_TYPE_RELAY_INFO_RESPONSE,
42 + Payload: response,
43 + })
44 +}
45 +
46 +func (g *RelayServer) handleLeaseUpdateRequest(ctx *StreamContext, packet *rdverb.Packet) error {
47 + var signedPayload rdsec.SignedPayload
48 + err := signedPayload.UnmarshalVT(packet.Payload)
49 + if err != nil {
50 + return err
51 + }
52 +
53 + var req rdverb.LeaseUpdateRequest
54 + err = req.UnmarshalVT(signedPayload.Data)
55 + if err != nil {
56 + return err
57 + }
58 +
59 + if !cryptoops.VerifySignedPayload(&signedPayload, req.Lease.Identity) {
60 + return err
61 + }
62 +
63 + var resp rdverb.LeaseUpdateResponse
64 +
65 + // Update lease in lease manager
66 + if g.leaseManager.UpdateLease(req.Lease, ctx.ConnectionID) {
67 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_ACCEPTED
68 +
69 + // Register lease connection
70 + leaseID := string(req.Lease.Identity.Id)
71 + g.leaseConnectionsLock.Lock()
72 + g.leaseConnections[leaseID] = ctx.Connection
73 + g.leaseConnectionsLock.Unlock()
74 + } else {
75 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_INVALID_EXPIRES
76 + }
77 +
78 + response, err := resp.MarshalVT()
79 + if err != nil {
80 + return err
81 + }
82 +
83 + return writePacket(ctx.Stream, &rdverb.Packet{
84 + Type: rdverb.PacketType_PACKET_TYPE_LEASE_UPDATE_RESPONSE,
85 + Payload: response,
86 + })
87 +}
88 +
89 +func (g *RelayServer) handleLeaseDeleteRequest(ctx *StreamContext, packet *rdverb.Packet) error {
90 + var signedPayload rdsec.SignedPayload
91 + err := signedPayload.UnmarshalVT(packet.Payload)
92 + if err != nil {
93 + return err
94 + }
95 +
96 + var req rdverb.LeaseDeleteRequest
97 + err = req.UnmarshalVT(signedPayload.Data)
98 + if err != nil {
99 + return err
100 + }
101 +
102 + if !cryptoops.VerifySignedPayload(&signedPayload, req.Identity) {
103 + return err
104 + }
105 +
106 + var resp rdverb.LeaseDeleteResponse
107 +
108 + // Delete lease from lease manager
109 + if g.leaseManager.DeleteLease(req.Identity) {
110 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_ACCEPTED
111 +
112 + // Remove lease connection
113 + leaseID := string(req.Identity.Id)
114 + g.leaseConnectionsLock.Lock()
115 + delete(g.leaseConnections, leaseID)
116 + g.leaseConnectionsLock.Unlock()
117 + } else {
118 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_INVALID_IDENTITY
119 + }
120 +
121 + response, err := resp.MarshalVT()
122 + if err != nil {
123 + return err
124 + }
125 +
126 + return writePacket(ctx.Stream, &rdverb.Packet{
127 + Type: rdverb.PacketType_PACKET_TYPE_LEASE_DELETE_RESPONSE,
128 + Payload: response,
129 + })
130 +}
131 +
132 +func (g *RelayServer) handleConnectionRequest(ctx *StreamContext, packet *rdverb.Packet) error {
133 + var req rdverb.ConnectionRequest
134 + err := req.UnmarshalVT(packet.Payload)
135 + if err != nil {
136 + return err
137 + }
138 +
139 + var resp rdverb.ConnectionResponse
140 +
141 + // Check if lease exists and get lease connection
142 + leaseEntry, exists := g.leaseManager.GetLease(req.ClientIdentity)
143 + if !exists {
144 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_INVALID_IDENTITY
145 + } else {
146 + // Get the lease connection using connection ID
147 + g.connectionsLock.RLock()
148 + leaseConn, leaseExists := g.connections[leaseEntry.ConnectionID]
149 + g.connectionsLock.RUnlock()
150 +
151 + if !leaseExists {
152 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_INVALID_IDENTITY
153 + } else {
154 + // Forward the connection request to the lease holder
155 + forwardResp, err := g.forwardConnectionRequest(leaseConn, &req)
156 + if err != nil {
157 + resp.Code = rdverb.ResponseCode_RESPONSE_CODE_REJECTED
158 + } else {
159 + resp.Code = forwardResp.Code
160 +
161 + // If accepted, set up bidirectional forwarding
162 + if resp.Code == rdverb.ResponseCode_RESPONSE_CODE_ACCEPTED {
163 + ctx.Hijack()
164 + go g.setupBidirectionalForwarding(ctx.Stream, leaseConn, leaseEntry)
165 + }
166 + }
167 + }
168 + }
169 +
170 + response, err := resp.MarshalVT()
171 + if err != nil {
172 + return err
173 + }
174 +
175 + return writePacket(ctx.Stream, &rdverb.Packet{
176 + Type: rdverb.PacketType_PACKET_TYPE_CONNECTION_RESPONSE,
177 + Payload: response,
178 + })
179 +}
180 +
181 +func (g *RelayServer) forwardConnectionRequest(leaseConn *Connection, req *rdverb.ConnectionRequest) (*rdverb.ConnectionResponse, error) {
182 + // Open a new stream to the lease holder
183 + forwardStream, err := leaseConn.sess.OpenStream()
184 + if err != nil {
185 + return nil, err
186 + }
187 + defer forwardStream.Close()
188 +
189 + // Forward the connection request
190 + requestPayload, err := req.MarshalVT()
191 + if err != nil {
192 + return nil, err
193 + }
194 +
195 + err = writePacket(forwardStream, &rdverb.Packet{
196 + Type: rdverb.PacketType_PACKET_TYPE_CONNECTION_REQUEST,
197 + Payload: requestPayload,
198 + })
199 + if err != nil {
200 + return nil, err
201 + }
202 +
203 + // Read the response
204 + respPacket, err := readPacket(forwardStream)
205 + if err != nil {
206 + return nil, err
207 + }
208 +
209 + if respPacket.Type != rdverb.PacketType_PACKET_TYPE_CONNECTION_RESPONSE {
210 + return nil, err
211 + }
212 +
213 + var resp rdverb.ConnectionResponse
214 + err = resp.UnmarshalVT(respPacket.Payload)
215 + if err != nil {
216 + return nil, err
217 + }
218 + return &resp, nil
219 +}
220 +
221 +func (g *RelayServer) setupBidirectionalForwarding(clientStream *yamux.Stream, leaseConn *Connection, leaseEntry *LeaseEntry) {
222 + // Open a new stream to the lease holder for data forwarding
223 + dataStream, err := leaseConn.sess.OpenStream()
224 + if err != nil {
225 + return
226 + }
227 + defer dataStream.Close()
228 +
229 + // Send a special packet to indicate this is a data stream
230 + initPacket := &rdverb.Packet{
231 + Type: rdverb.PacketType_PACKET_TYPE_CONNECTION_REQUEST, // Reuse as init signal
232 + Payload: []byte("DATA_STREAM"),
233 + }
234 +
235 + err = writePacket(dataStream, initPacket)
236 + if err != nil {
237 + return
238 + }
239 +
240 + // Read the response to confirm data stream is ready
241 + respPacket, err := readPacket(dataStream)
242 + if err != nil {
243 + return
244 + }
245 +
246 + // Check if we got a data stream confirmation
247 + if respPacket.Type != rdverb.PacketType_PACKET_TYPE_CONNECTION_RESPONSE {
248 + return
249 + }
250 +
251 + var resp rdverb.ConnectionResponse
252 + err = resp.UnmarshalVT(respPacket.Payload)
253 + if err != nil {
254 + return
255 + }
256 +
257 + if resp.Code != rdverb.ResponseCode_RESPONSE_CODE_ACCEPTED {
258 + return
259 + }
260 +
261 + // Track this relayed connection
262 + leaseID := string(leaseEntry.Lease.Identity.Id)
263 + g.relayedConnectionsLock.Lock()
264 + g.relayedConnections[leaseID] = append(g.relayedConnections[leaseID], clientStream)
265 + g.relayedConnectionsLock.Unlock()
266 +
267 + // Set up bidirectional copying with cleanup
268 + var wg sync.WaitGroup
269 + wg.Add(2)
270 +
271 + // Copy from client to lease holder
272 + go func() {
273 + defer wg.Done()
274 + io.Copy(dataStream, clientStream)
275 + }()
276 +
277 + // Copy from lease holder to client
278 + go func() {
279 + defer wg.Done()
280 + io.Copy(clientStream, dataStream)
281 + }()
282 +
283 + wg.Wait()
284 +
285 + // Clean up relayed connection tracking when done
286 + g.relayedConnectionsLock.Lock()
287 + if streams, exists := g.relayedConnections[leaseID]; exists {
288 + // Remove this stream from the slice
289 + for i, stream := range streams {
290 + if stream == clientStream {
291 + g.relayedConnections[leaseID] = append(streams[:i], streams[i+1:]...)
292 + break
293 + }
294 + }
295 + // If no more streams for this lease, remove the entry
296 + if len(g.relayedConnections[leaseID]) == 0 {
297 + delete(g.relayedConnections, leaseID)
298 + }
299 + }
300 + g.relayedConnectionsLock.Unlock()
301 +}
302 +
303 +// Helper function to read packet from stream
304 +func readPacket(stream io.Reader) (*rdverb.Packet, error) {
305 + var size [4]byte
306 +
307 + _, err := io.ReadFull(stream, size[:])
308 + if err != nil {
309 + return nil, err
310 + }
311 +
312 + n := int(binary.BigEndian.Uint32(size[:]))
313 + if n > _MAX_RAW_PACKET_SIZE {
314 + return nil, err
315 + }
316 +
317 + buffer := bytebufferpool.Get()
318 + defer bytebufferpool.Put(buffer)
319 +
320 + bufferGrow(buffer, n)
321 +
322 + _, err = io.ReadFull(stream, buffer.B[:n])
323 + if err != nil {
324 + return nil, err
325 + }
326 +
327 + var packet rdverb.Packet
328 + err = packet.UnmarshalVT(buffer.B[:n])
329 + if err != nil {
330 + return nil, err
331 + }
332 +
333 + return &packet, nil
334 +}
relaydns/helper.go new
+48
@@ -0,0 +1,48 @@
1 +package relaydns
2 +
3 +import (
4 + "encoding/binary"
5 + "io"
6 +
7 + "github.com/gosuda/relaydns/relaydns/core/proto/rdverb"
8 + "github.com/valyala/bytebufferpool"
9 +)
10 +
11 +func bufferGrow(buffer *bytebufferpool.ByteBuffer, n int) {
12 + if n > cap(buffer.B) {
13 + buffer.B = make([]byte, ((n+(1<<14)-1)/1<<14)*(1<<14))
14 + }
15 +}
16 +
17 +func decodeProtobuf[T interface {
18 + UnmarshalVT(data []byte) error
19 +}](
20 + data []byte,
21 +) (
22 + T,
23 + error,
24 +) {
25 + var t T
26 + err := t.UnmarshalVT(data)
27 + if err != nil {
28 + return t, err
29 + }
30 + return t, nil
31 +}
32 +
33 +func writePacket(w io.Writer, packet *rdverb.Packet) error {
34 + payload, err := packet.MarshalVT()
35 + if err != nil {
36 + return err
37 + }
38 +
39 + buffer := bytebufferpool.Get()
40 + defer bytebufferpool.Put(buffer)
41 +
42 + var size [4]byte
43 + binary.BigEndian.PutUint32(size[:], uint32(len(payload)))
44 + buffer.Write(size[:])
45 + buffer.Write(payload)
46 + _, err = w.Write(buffer.B)
47 + return err
48 +}
relaydns/host.go deleted
-101
@@ -1,101 +0,0 @@
1 -package relaydns
2 -
3 -import (
4 - "context"
5 - "fmt"
6 -
7 - "github.com/libp2p/go-libp2p"
8 - "github.com/libp2p/go-libp2p/core/host"
9 - "github.com/libp2p/go-libp2p/core/network"
10 - "github.com/libp2p/go-libp2p/core/peer"
11 - ma "github.com/multiformats/go-multiaddr"
12 - "github.com/rs/zerolog/log"
13 -)
14 -
15 -func MakeHost(ctx context.Context, port int, enableRelay bool) (host.Host, error) {
16 - addrs := []string{
17 - fmt.Sprintf("/ip4/0.0.0.0/tcp/%d", port),
18 - fmt.Sprintf("/ip4/0.0.0.0/udp/%d/quic-v1", port),
19 - fmt.Sprintf("/ip6/::/tcp/%d", port),
20 - fmt.Sprintf("/ip6/::/udp/%d/quic-v1", port),
21 - }
22 -
23 - opts := []libp2p.Option{
24 - libp2p.ListenAddrStrings(addrs...),
25 - libp2p.DefaultTransports, // TCP+QUIC
26 - libp2p.NATPortMap(),
27 - libp2p.EnableNATService(), // AutoNAT helper
28 - libp2p.EnableHolePunching(), // DCUtR
29 - libp2p.DefaultSecurity,
30 - libp2p.DefaultMuxers,
31 - }
32 - if enableRelay {
33 - opts = append(opts, libp2p.EnableRelay()) // circuit relay (useful both as client & svc)
34 - }
35 - h, err := libp2p.New(opts...)
36 - if err != nil {
37 - return nil, err
38 - }
39 - return h, nil
40 -}
41 -
42 -func ConnectBootstraps(ctx context.Context, h host.Host, addrs []string) {
43 - // Aggregate all multiaddrs per peer and dial them together so the dialer
44 - // can fall back from loopback to routable addresses.
45 - perPeer := make(map[peer.ID][]ma.Multiaddr)
46 -
47 - for _, s := range addrs {
48 - m, err := ma.NewMultiaddr(s)
49 - if err != nil {
50 - log.Warn().Err(err).Msgf("bootstrap bad multiaddr %q", s)
51 - continue
52 - }
53 - ai, err := peer.AddrInfoFromP2pAddr(m)
54 - if err != nil {
55 - log.Warn().Err(err).Msgf("bootstrap missing /p2p/ in %q", s)
56 - continue
57 - }
58 - // Prefer the addr(s) returned by AddrInfoFromP2pAddr (base part without /p2p)
59 - bases := ai.Addrs
60 - if len(bases) == 0 {
61 - // Fallback: try to decapsulate /p2p component manually
62 - dec := m
63 - // Construct a /p2p/<peerID> multiaddr for decapsulation
64 - p2pComp, derr := ma.NewMultiaddr(fmt.Sprintf("/p2p/%s", ai.ID.String()))
65 - if derr == nil {
66 - dec = m.Decapsulate(p2pComp)
67 - }
68 - if dec != nil && dec.String() != "" {
69 - bases = []ma.Multiaddr{dec}
70 - }
71 - }
72 - if len(bases) == 0 {
73 - continue
74 - }
75 - // Append while de-duplicating per peer, preserving original order.
76 - cur := perPeer[ai.ID]
77 - seen := make(map[string]struct{}, len(cur))
78 - for _, a := range cur {
79 - seen[a.String()] = struct{}{}
80 - }
81 - for _, a := range bases {
82 - if _, ok := seen[a.String()]; ok {
83 - continue
84 - }
85 - cur = append(cur, a)
86 - seen[a.String()] = struct{}{}
87 - }
88 - perPeer[ai.ID] = cur
89 - }
90 -
91 - // Now attempt a single connect per peer with all known addresses.
92 - for pid, maddrs := range perPeer {
93 - if h.Network().Connectedness(pid) == network.Connected {
94 - continue
95 - }
96 - info := peer.AddrInfo{ID: pid, Addrs: maddrs}
97 - if err := h.Connect(ctx, info); err != nil {
98 - log.Warn().Err(err).Msgf("bootstrap connect %s", pid)
99 - }
100 - }
101 -}
relaydns/internal/.gitkeep renamed
relaydns/internal/wsstream/wsstream.go new
+42
@@ -0,0 +1,42 @@
1 +package relaydns
2 +
3 +import (
4 + "io"
5 +
6 + "github.com/gorilla/websocket"
7 +)
8 +
9 +type wsStream struct {
10 + c *websocket.Conn
11 + currentReader io.Reader
12 +}
13 +
14 +func (g *wsStream) Read(p []byte) (n int, err error) {
15 + if g.currentReader == nil {
16 + _, reader, err := g.c.NextReader()
17 + if err != nil {
18 + return 0, err
19 + }
20 + g.currentReader = reader
21 + }
22 +
23 + n, err = g.currentReader.Read(p)
24 + if err == io.EOF {
25 + g.currentReader = nil
26 + err = nil
27 + }
28 +
29 + return n, err
30 +}
31 +
32 +func (g *wsStream) Write(p []byte) (n int, err error) {
33 + err = g.c.WriteMessage(websocket.BinaryMessage, p)
34 + if err != nil {
35 + return 0, err
36 + }
37 + return len(p), nil
38 +}
39 +
40 +func (g *wsStream) Close() error {
41 + return g.c.Close()
42 +}
relaydns/lease.go new
+148
@@ -0,0 +1,148 @@
1 +package relaydns
2 +
3 +import (
4 + "sync"
5 + "time"
6 +
7 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
8 + "github.com/gosuda/relaydns/relaydns/core/proto/rdverb"
9 +)
10 +
11 +type LeaseEntry struct {
12 + Lease *rdverb.Lease
13 + Expires time.Time
14 + LastSeen time.Time
15 + ConnectionID int64 // Store the connection ID
16 +}
17 +
18 +type LeaseManager struct {
19 + leases map[string]*LeaseEntry // Key: identity ID
20 + leasesLock sync.RWMutex
21 + stopCh chan struct{}
22 + ttlInterval time.Duration
23 +}
24 +
25 +func NewLeaseManager(ttlInterval time.Duration) *LeaseManager {
26 + return &LeaseManager{
27 + leases: make(map[string]*LeaseEntry),
28 + stopCh: make(chan struct{}),
29 + ttlInterval: ttlInterval,
30 + }
31 +}
32 +
33 +func (lm *LeaseManager) Start() {
34 + go lm.ttlWorker()
35 +}
36 +
37 +func (lm *LeaseManager) Stop() {
38 + close(lm.stopCh)
39 +}
40 +
41 +func (lm *LeaseManager) ttlWorker() {
42 + ticker := time.NewTicker(lm.ttlInterval)
43 + defer ticker.Stop()
44 +
45 + for {
46 + select {
47 + case <-ticker.C:
48 + lm.cleanupExpiredLeases()
49 + case <-lm.stopCh:
50 + return
51 + }
52 + }
53 +}
54 +
55 +func (lm *LeaseManager) cleanupExpiredLeases() {
56 + lm.leasesLock.Lock()
57 + defer lm.leasesLock.Unlock()
58 +
59 + now := time.Now()
60 + for id, lease := range lm.leases {
61 + if now.After(lease.Expires) {
62 + delete(lm.leases, id)
63 + }
64 + }
65 +}
66 +
67 +func (lm *LeaseManager) UpdateLease(lease *rdverb.Lease, connectionID int64) bool {
68 + lm.leasesLock.Lock()
69 + defer lm.leasesLock.Unlock()
70 +
71 + identityID := string(lease.Identity.Id)
72 + expires := time.Unix(lease.Expires, 0)
73 +
74 + // Check if lease is already expired
75 + if time.Now().After(expires) {
76 + return false
77 + }
78 +
79 + lm.leases[identityID] = &LeaseEntry{
80 + Lease: lease,
81 + Expires: expires,
82 + LastSeen: time.Now(),
83 + ConnectionID: connectionID,
84 + }
85 +
86 + return true
87 +}
88 +
89 +func (lm *LeaseManager) DeleteLease(identity *rdsec.Identity) bool {
90 + lm.leasesLock.Lock()
91 + defer lm.leasesLock.Unlock()
92 +
93 + identityID := string(identity.Id)
94 + if _, exists := lm.leases[identityID]; exists {
95 + delete(lm.leases, identityID)
96 + return true
97 + }
98 + return false
99 +}
100 +
101 +func (lm *LeaseManager) GetLease(identity *rdsec.Identity) (*LeaseEntry, bool) {
102 + lm.leasesLock.RLock()
103 + defer lm.leasesLock.RUnlock()
104 +
105 + identityID := string(identity.Id)
106 + lease, exists := lm.leases[identityID]
107 + if !exists {
108 + return nil, false
109 + }
110 +
111 + // Check if lease is expired
112 + if time.Now().After(lease.Expires) {
113 + return nil, false
114 + }
115 +
116 + return lease, true
117 +}
118 +
119 +func (lm *LeaseManager) GetAllLeases() []*rdverb.Lease {
120 + lm.leasesLock.RLock()
121 + defer lm.leasesLock.RUnlock()
122 +
123 + now := time.Now()
124 + var validLeases []*rdverb.Lease
125 +
126 + for _, lease := range lm.leases {
127 + if now.Before(lease.Expires) {
128 + validLeases = append(validLeases, lease.Lease)
129 + }
130 + }
131 +
132 + return validLeases
133 +}
134 +
135 +func (lm *LeaseManager) CleanupLeasesByConnectionID(connectionID int64) []string {
136 + lm.leasesLock.Lock()
137 + defer lm.leasesLock.Unlock()
138 +
139 + var cleanedLeaseIDs []string
140 + for leaseID, lease := range lm.leases {
141 + if lease.ConnectionID == connectionID {
142 + delete(lm.leases, leaseID)
143 + cleanedLeaseIDs = append(cleanedLeaseIDs, leaseID)
144 + }
145 + }
146 +
147 + return cleanedLeaseIDs
148 +}
relaydns/relay.go new
+204
@@ -0,0 +1,204 @@
1 +package relaydns
2 +
3 +import (
4 + "io"
5 + "sync"
6 + "time"
7 +
8 + "github.com/gosuda/relaydns/relaydns/core/cryptoops"
9 + "github.com/gosuda/relaydns/relaydns/core/proto/rdsec"
10 + "github.com/gosuda/relaydns/relaydns/core/proto/rdverb"
11 + "github.com/hashicorp/yamux"
12 +)
13 +
14 +type Connection struct {
15 + conn io.ReadWriteCloser
16 + sess *yamux.Session
17 +
18 + streams map[uint32]*yamux.Stream
19 + streamsLock sync.Mutex
20 +}
21 +
22 +type RelayServer struct {
23 + credential *cryptoops.Credential
24 + identity *rdsec.Identity
25 + address []string
26 +
27 + connidCounter int64
28 + connections map[int64]*Connection
29 + connectionsLock sync.RWMutex
30 +
31 + leaseConnections map[string]*Connection // Key: lease ID, Value: Connection
32 + leaseConnectionsLock sync.RWMutex
33 +
34 + relayedConnections map[string][]*yamux.Stream // Key: lease ID, Value: slice of relayed streams
35 + relayedConnectionsLock sync.RWMutex
36 +
37 + leaseManager *LeaseManager
38 +
39 + stopch chan struct{}
40 + waitgroup sync.WaitGroup
41 +}
42 +
43 +func NewRelayServer(credential *cryptoops.Credential, address []string) *RelayServer {
44 + return &RelayServer{
45 + credential: credential,
46 + identity: &rdsec.Identity{
47 + Id: credential.ID(),
48 + PublicKey: credential.PublicKey(),
49 + },
50 + address: address,
51 + connidCounter: 0,
52 + connections: make(map[int64]*Connection),
53 + leaseConnections: make(map[string]*Connection),
54 + relayedConnections: make(map[string][]*yamux.Stream),
55 + leaseManager: NewLeaseManager(30 * time.Second), // TTL check every 30 seconds
56 + stopch: make(chan struct{}),
57 + }
58 +}
59 +
60 +var _yamux_config = yamux.DefaultConfig()
61 +
62 +func (g *RelayServer) handleConn(id int64, connection *Connection) {
63 + defer func() {
64 + // Clean up leases associated with this connection when it closes
65 + cleanedLeaseIDs := g.leaseManager.CleanupLeasesByConnectionID(id)
66 +
67 + // Also clean up lease connections mapping
68 + g.leaseConnectionsLock.Lock()
69 + for _, leaseID := range cleanedLeaseIDs {
70 + delete(g.leaseConnections, leaseID)
71 + }
72 + g.leaseConnectionsLock.Unlock()
73 +
74 + // Clean up relayed connections for these leases
75 + g.relayedConnectionsLock.Lock()
76 + for _, leaseID := range cleanedLeaseIDs {
77 + if streams, exists := g.relayedConnections[leaseID]; exists {
78 + // Close all relayed streams
79 + for _, stream := range streams {
80 + stream.Close()
81 + }
82 + delete(g.relayedConnections, leaseID)
83 + }
84 + }
85 + g.relayedConnectionsLock.Unlock()
86 +
87 + // Remove the connection itself
88 + g.connectionsLock.Lock()
89 + delete(g.connections, id)
90 + g.connectionsLock.Unlock()
91 +
92 + // Close the underlying connection
93 + connection.conn.Close()
94 + }()
95 +
96 + for {
97 + stream, err := connection.sess.AcceptStream()
98 + if err != nil {
99 + return
100 + }
101 + connection.streamsLock.Lock()
102 + connection.streams[stream.StreamID()] = stream
103 + connection.streamsLock.Unlock()
104 + go g.handleStream(stream, id, connection)
105 + }
106 +}
107 +
108 +const _MAX_RAW_PACKET_SIZE = 1 << 26 // 64MB
109 +
110 +func (g *RelayServer) handleStream(stream *yamux.Stream, id int64, connection *Connection) {
111 + var hijacked bool = false
112 + defer func() {
113 + stream_id := stream.StreamID()
114 + if !hijacked {
115 + connection.streamsLock.Lock()
116 + stream.Close()
117 + delete(connection.streams, stream_id)
118 + connection.streamsLock.Unlock()
119 + }
120 + }()
121 +
122 + ctx := &StreamContext{
123 + Server: g,
124 + Stream: stream,
125 + Connection: connection,
126 + ConnectionID: id,
127 + Hijacked: &hijacked,
128 + }
129 +
130 + for {
131 + packet, err := readPacket(stream)
132 + if err != nil {
133 + return
134 + }
135 +
136 + switch packet.Type {
137 + case rdverb.PacketType_PACKET_TYPE_RELAY_INFO_REQUEST:
138 + err = g.handleRelayInfoRequest(ctx, packet)
139 + case rdverb.PacketType_PACKET_TYPE_LEASE_UPDATE_REQUEST:
140 + err = g.handleLeaseUpdateRequest(ctx, packet)
141 + case rdverb.PacketType_PACKET_TYPE_LEASE_DELETE_REQUEST:
142 + err = g.handleLeaseDeleteRequest(ctx, packet)
143 + case rdverb.PacketType_PACKET_TYPE_CONNECTION_REQUEST:
144 + err = g.handleConnectionRequest(ctx, packet)
145 + default:
146 + // Unknown packet type, return to close the stream
147 + return
148 + }
149 +
150 + if err != nil {
151 + return
152 + }
153 +
154 + // If the stream was hijacked, exit the loop
155 + if hijacked {
156 + return
157 + }
158 + }
159 +}
160 +
161 +func (g *RelayServer) HandleConnection(conn io.ReadWriteCloser) error {
162 + sess, err := yamux.Server(conn, _yamux_config)
163 + if err != nil {
164 + return err
165 + }
166 +
167 + g.connectionsLock.Lock()
168 + g.connidCounter++
169 + connection := &Connection{
170 + conn: conn,
171 + sess: sess,
172 + streams: make(map[uint32]*yamux.Stream),
173 + }
174 + g.connections[g.connidCounter] = connection
175 + g.connectionsLock.Unlock()
176 +
177 + go g.handleConn(g.connidCounter, connection)
178 +
179 + return nil
180 +}
181 +
182 +func (g *RelayServer) relayInfo() *rdverb.RelayInfo {
183 + leases := g.leaseManager.GetAllLeases()
184 + var leaseIds []string
185 + for _, lease := range leases {
186 + leaseIds = append(leaseIds, string(lease.Identity.Id))
187 + }
188 +
189 + return &rdverb.RelayInfo{
190 + Identity: g.identity,
191 + Address: g.address,
192 + Leases: leaseIds,
193 + }
194 +}
195 +
196 +func (g *RelayServer) Start() {
197 + g.leaseManager.Start()
198 +}
199 +
200 +func (g *RelayServer) Stop() {
201 + close(g.stopch)
202 + g.leaseManager.Stop()
203 + g.waitgroup.Wait()
204 +}
relaydns/server.go deleted
-335
@@ -1,335 +0,0 @@
1 -package relaydns
2 -
3 -import (
4 - "bufio"
5 - "context"
6 - "encoding/json"
7 - "fmt"
8 - "io"
9 - "net"
10 - "net/http"
11 - "net/url"
12 - "sort"
13 - "strings"
14 - "sync"
15 - "time"
16 -
17 - pubsub "github.com/libp2p/go-libp2p-pubsub"
18 - "github.com/libp2p/go-libp2p/core/host"
19 - "github.com/libp2p/go-libp2p/core/peer"
20 - "github.com/libp2p/go-libp2p/core/protocol"
21 - ma "github.com/multiformats/go-multiaddr"
22 - "github.com/rs/zerolog/log"
23 -)
24 -
25 -type RelayServer struct {
26 - ctx context.Context
27 - h host.Host
28 - protocol string
29 - topicName string
30 - sub *pubsub.Subscription
31 -
32 - storeMu sync.Mutex
33 - store map[string]HostEntry
34 - ttl time.Duration
35 - deadTTL time.Duration
36 -
37 - wg sync.WaitGroup
38 -}
39 -
40 -func NewRelayServer(ctx context.Context, h host.Host, protocol, topic string) (*RelayServer, error) {
41 - ps, err := pubsub.NewGossipSub(ctx, h)
42 - if err != nil {
43 - return nil, err
44 - }
45 - t, err := ps.Join(topic)
46 - if err != nil {
47 - return nil, err
48 - }
49 - sub, err := t.Subscribe()
50 - if err != nil {
51 - return nil, err
52 - }
53 - d := &RelayServer{
54 - ctx: ctx,
55 - h: h,
56 - protocol: protocol,
57 - topicName: topic,
58 - sub: sub,
59 - store: map[string]HostEntry{},
60 - ttl: 15 * time.Second,
61 - deadTTL: 1 * time.Minute,
62 - }
63 - d.wg.Add(2)
64 - go d.collect()
65 - go d.gc()
66 - return d, nil
67 -}
68 -
69 -func (s *RelayServer) Close() error {
70 - s.sub.Cancel()
71 - s.wg.Wait()
72 - return nil
73 -}
74 -
75 -func (s *RelayServer) collect() {
76 - defer s.wg.Done()
77 - for {
78 - msg, err := s.sub.Next(s.ctx)
79 - if err != nil {
80 - return
81 - }
82 - var ad Advertise
83 - if err := json.Unmarshal(msg.Data, &ad); err != nil {
84 - continue
85 - }
86 - var ai *peer.AddrInfo
87 - // pick any addr that includes /p2p/ (dnsaddr resolved entries will)
88 - for _, s := range ad.Addrs {
89 - m, err := ma.NewMultiaddr(s)
90 - if err != nil {
91 - continue
92 - }
93 - if a, err := peer.AddrInfoFromP2pAddr(m); err == nil {
94 - ai = a
95 - break
96 - }
97 - }
98 - if ai == nil {
99 - continue
100 - }
101 - now := time.Now()
102 - s.storeMu.Lock()
103 - _, existed := s.store[ad.Peer]
104 - s.store[ad.Peer] = HostEntry{Info: ad, AddrInfo: ai, LastSeen: now, Connected: true}
105 - // refresh picker snapshot
106 - snap := make([]HostEntry, 0, len(s.store))
107 - for _, v := range s.store {
108 - snap = append(snap, v)
109 - }
110 - s.storeMu.Unlock()
111 - if !existed {
112 - log.Info().Str("peer", ad.Peer).Str("name", ad.Name).Msg("server: add new client")
113 - }
114 - _ = snap // snapshot kept local; selection handled explicitly via /peer
115 - }
116 -}
117 -
118 -func (s *RelayServer) gc() {
119 - defer s.wg.Done()
120 - t := time.NewTicker(5 * time.Second)
121 - defer t.Stop()
122 - for {
123 - select {
124 - case <-s.ctx.Done():
125 - return
126 - case <-t.C:
127 - now := time.Now()
128 - removed := make([]HostEntry, 0)
129 - s.storeMu.Lock()
130 - for k, v := range s.store {
131 - // Prefer client-provided TTL if present; fallback to default d.ttl
132 - ttl := s.ttl
133 - if v.Info.TTL > 0 {
134 - ttl = time.Duration(v.Info.TTL) * time.Second
135 - }
136 - // mark disconnected after ttl
137 - if now.Sub(v.LastSeen) > ttl && v.Connected {
138 - v.Connected = false
139 - s.store[k] = v
140 - }
141 - // remove only after extended dead TTL
142 - deadAfter := s.deadTTL
143 - if v.Info.TTL > 0 {
144 - da := time.Duration(v.Info.TTL) * time.Second * 5
145 - if da > deadAfter {
146 - deadAfter = da
147 - }
148 - }
149 - if now.Sub(v.LastSeen) > deadAfter {
150 - removed = append(removed, v)
151 - delete(s.store, k)
152 - }
153 - }
154 - snap := make([]HostEntry, 0, len(s.store))
155 - for _, v := range s.store {
156 - snap = append(snap, v)
157 - }
158 - s.storeMu.Unlock()
159 - for _, r := range removed {
160 - log.Info().Str("peer", r.Info.Peer).Str("name", r.Info.Name).Dur("idle", now.Sub(r.LastSeen)).Msg("server: removed stale client")
161 - }
162 - _ = snap
163 - }
164 - }
165 -}
166 -
167 -// Hosts returns a snapshot of current known hosts.
168 -func (s *RelayServer) Hosts() []HostEntry {
169 - s.storeMu.Lock()
170 - defer s.storeMu.Unlock()
171 - list := make([]HostEntry, 0, len(s.store))
172 - for _, v := range s.store {
173 - list = append(list, v)
174 - }
175 - sort.SliceStable(list, func(i, j int) bool {
176 - li, lj := list[i], list[j]
177 - if li.Connected != lj.Connected {
178 - return li.Connected // true before false
179 - }
180 - // Normalize names for comparison; fallback to peer id if empty
181 - nameI := strings.ToLower(strings.TrimSpace(li.Info.Name))
182 - if nameI == "" {
183 - nameI = strings.ToLower(li.Info.Peer)
184 - }
185 - nameJ := strings.ToLower(strings.TrimSpace(lj.Info.Name))
186 - if nameJ == "" {
187 - nameJ = strings.ToLower(lj.Info.Peer)
188 - }
189 - if nameI != nameJ {
190 - return nameI < nameJ
191 - }
192 - // As a final tiebreaker, keep most recent first for stability
193 - return li.LastSeen.After(lj.LastSeen)
194 - })
195 - return list
196 -}
197 -
198 -// ProxyHTTP proxies the given HTTP request to the specified peer and writes the response to w.
199 -func (d *RelayServer) ProxyHTTP(w http.ResponseWriter, r *http.Request, peerID, pathSuffix string) {
200 - d.storeMu.Lock()
201 - entry, ok := d.store[peerID]
202 - d.storeMu.Unlock()
203 - if !ok || entry.AddrInfo == nil {
204 - http.Error(w, "peer not found", http.StatusNotFound)
205 - return
206 - }
207 - if err := d.h.Connect(d.ctx, *entry.AddrInfo); err != nil {
208 - log.Error().Err(err).Msgf("connect %s failed", entry.AddrInfo.ID)
209 - http.Error(w, "upstream connect failed", http.StatusBadGateway)
210 - return
211 - }
212 - s, err := d.h.NewStream(d.ctx, entry.AddrInfo.ID, protocol.ID(d.protocol))
213 - if err != nil {
214 - log.Error().Err(err).Msg("new stream")
215 - http.Error(w, "open stream failed", http.StatusBadGateway)
216 - return
217 - }
218 - defer func() {
219 - if err := s.Close(); err != nil {
220 - log.Debug().Err(err).Msg("stream close")
221 - }
222 - }()
223 - outReq := r.Clone(d.ctx)
224 - outReq.URL = &url.URL{Path: pathSuffix, RawQuery: r.URL.RawQuery}
225 - outReq.RequestURI = ""
226 - if err := outReq.Write(s); err != nil {
227 - log.Error().Err(err).Msg("write upstream request")
228 - http.Error(w, "write upstream failed", http.StatusBadGateway)
229 - return
230 - }
231 - br := bufio.NewReader(s)
232 - resp, err := http.ReadResponse(br, outReq)
233 - if err != nil {
234 - log.Error().Err(err).Msg("read upstream response")
235 - http.Error(w, "bad upstream response", http.StatusBadGateway)
236 - return
237 - }
238 - defer func() {
239 - if err := resp.Body.Close(); err != nil {
240 - log.Debug().Err(err).Msg("response body close")
241 - }
242 - }()
243 -
244 - // Handle WebSocket Upgrade: write 101 response and then raw-tunnel bytes
245 - if resp.StatusCode == http.StatusSwitchingProtocols && strings.Contains(strings.ToLower(resp.Header.Get("Upgrade")), "websocket") {
246 - if hj, ok := w.(http.Hijacker); ok {
247 - clientConn, clientBuf, err := hj.Hijack()
248 - if err != nil {
249 - log.Error().Err(err).Msg("hijack client conn")
250 - return
251 - }
252 - defer func() {
253 - if err := clientConn.Close(); err != nil {
254 - log.Debug().Err(err).Msg("client conn close")
255 - }
256 - }()
257 - // Write upstream 101 response (headers)
258 - if err := resp.Write(clientBuf); err == nil {
259 - _ = clientBuf.Flush()
260 - }
261 - // Flush any bytes already buffered by http.ReadResponse's bufio.Reader
262 - if n := br.Buffered(); n > 0 {
263 - tmp := make([]byte, n)
264 - if _, err := io.ReadFull(br, tmp); err == nil {
265 - _, _ = clientConn.Write(tmp)
266 - }
267 - }
268 - // Raw byte tunnel between client and upstream stream (bidirectional)
269 - go func() {
270 - _, _ = io.Copy(s, clientConn)
271 - }()
272 - _, _ = io.Copy(clientConn, s)
273 - return
274 - }
275 - }
276 - for k, vv := range resp.Header {
277 - for _, v := range vv {
278 - w.Header().Add(k, v)
279 - }
280 - }
281 - w.WriteHeader(resp.StatusCode)
282 - // If upstream is SSE, forward with Flush to avoid buffering
283 - if strings.Contains(strings.ToLower(resp.Header.Get("Content-Type")), "text/event-stream") {
284 - if f, ok := w.(http.Flusher); ok {
285 - buf := make([]byte, 4096)
286 - for {
287 - n, err := resp.Body.Read(buf)
288 - if n > 0 {
289 - if _, werr := w.Write(buf[:n]); werr == nil {
290 - f.Flush()
291 - }
292 - }
293 - if err != nil {
294 - break
295 - }
296 - }
297 - return
298 - }
299 - }
300 - _, _ = io.Copy(w, resp.Body)
301 -}
302 -
303 -// ProxyTCP opens a libp2p stream to peerID using the Director protocol and
304 -// pipes raw bytes between the accepted TCP connection and the libp2p stream.
305 -func (d *RelayServer) ProxyTCP(c net.Conn, peerID string) error {
306 - defer func() {
307 - if err := c.Close(); err != nil {
308 - log.Debug().Err(err).Msg("tcp conn close")
309 - }
310 - }()
311 - d.storeMu.Lock()
312 - entry, ok := d.store[peerID]
313 - d.storeMu.Unlock()
314 - if !ok || entry.AddrInfo == nil {
315 - return fmt.Errorf("peer not found")
316 - }
317 - if err := d.h.Connect(d.ctx, *entry.AddrInfo); err != nil {
318 - return err
319 - }
320 - s, err := d.h.NewStream(d.ctx, entry.AddrInfo.ID, protocol.ID(d.protocol))
321 - if err != nil {
322 - return err
323 - }
324 - defer func() {
325 - if err := s.Close(); err != nil {
326 - log.Debug().Err(err).Msg("stream close")
327 - }
328 - }()
329 - // bidirectional copy
330 - go func() {
331 - _, _ = io.Copy(s, c)
332 - }()
333 - _, _ = io.Copy(c, s)
334 - return nil
335 -}
relaydns/types.go deleted
-58
@@ -1,58 +0,0 @@
1 -package relaydns
2 -
3 -import (
4 - "time"
5 -
6 - "github.com/libp2p/go-libp2p/core/peer"
7 -)
8 -
9 -// Defaults shared by server and client.
10 -const (
11 - DefaultProtocol = "/relaydns/http/1.0"
12 - DefaultTopic = "relaydns.backends"
13 -)
14 -
15 -type Hosts struct {
16 - ServerPeer string `json:"serverPeer"`
17 - ServerAddrs []string `json:"serverAddrs"`
18 - Peers []string `json:"peers"` // connected peer IDs
19 -}
20 -
21 -type Advertise struct {
22 - Peer string `json:"peer"`
23 - Name string `json:"name,omitempty"`
24 - DNS string `json:"dns,omitempty"`
25 - Addrs []string `json:"addrs"`
26 - Ready bool `json:"ready"`
27 - Load float64 `json:"load"`
28 - TS time.Time `json:"ts"`
29 - TTL int `json:"ttl,omitempty"`
30 - Proto string `json:"proto,omitempty"`
31 -}
32 -
33 -type HostEntry struct {
34 - Info Advertise
35 - AddrInfo *peer.AddrInfo
36 - LastSeen time.Time
37 - Connected bool
38 -}
39 -
40 -// AdminPage is a simple view model used by the server admin UI template.
41 -// It intentionally lives here so other binaries can share the same model if needed.
42 -type AdminPage struct {
43 - NodeID string
44 - Addrs []string
45 - Rows []AdminRow
46 -}
47 -
48 -// AdminRow represents a single backend entry as shown on the admin index.
49 -type AdminRow struct {
50 - Peer string
51 - Name string
52 - DNS string
53 - LastSeen string
54 - Link string
55 - TTL string
56 - Connected bool
57 - Kind string
58 -}
relaydns/utils.go deleted
-88
@@ -1,88 +0,0 @@
1 -package relaydns
2 -
3 -import (
4 - "encoding/json"
5 - "fmt"
6 - "net/http"
7 - "net/url"
8 - "sort"
9 - "strings"
10 - "time"
11 -
12 - "github.com/libp2p/go-libp2p/core/host"
13 - "github.com/rs/zerolog/log"
14 -)
15 -
16 -func BuildAddrs(h host.Host) []string {
17 - out := make([]string, 0)
18 - for _, a := range h.Addrs() {
19 - out = append(out, fmt.Sprintf("%s/p2p/%s", a.String(), h.ID().String()))
20 - }
21 - return out
22 -}
23 -
24 -func SortMultiaddrs(addrs []string, preferQUIC, preferLocal bool) {
25 - score := func(a string) int {
26 - sc := 0
27 - if preferQUIC && strings.Contains(a, "/quic-v1") {
28 - sc += 2
29 - }
30 - if preferLocal && (strings.Contains(a, "/ip4/127.0.0.1/") || strings.Contains(a, "/ip6/::1/")) {
31 - sc += 1
32 - }
33 - return sc
34 - }
35 - sort.SliceStable(addrs, func(i, j int) bool { return score(addrs[i]) > score(addrs[j]) })
36 -}
37 -
38 -func RemoveDuplicate(ss []string) []string {
39 - seen := map[string]struct{}{}
40 - out := make([]string, 0, len(ss))
41 - for _, s := range ss {
42 - if _, ok := seen[s]; ok {
43 - continue
44 - }
45 - seen[s] = struct{}{}
46 - out = append(out, s)
47 - }
48 - return out
49 -}
50 -
51 -func FetchMultiaddrsFromHosts(base string, timeout time.Duration) ([]string, error) {
52 - u, err := url.Parse(base)
53 - if err != nil {
54 - return nil, fmt.Errorf("parse server-url: %w", err)
55 - }
56 - // ensure path ends with /hosts
57 - if !strings.HasSuffix(u.Path, "/hosts") {
58 - if u.Path == "" || u.Path == "/" {
59 - u.Path = "/hosts"
60 - } else {
61 - u.Path = strings.TrimSuffix(u.Path, "/") + "/hosts"
62 - }
63 - }
64 - client := &http.Client{Timeout: timeout}
65 - req, _ := http.NewRequest(http.MethodGet, u.String(), nil)
66 - resp, err := client.Do(req)
67 - if err != nil {
68 - return nil, err
69 - }
70 - defer func() {
71 - if err := resp.Body.Close(); err != nil {
72 - log.Debug().Err(err).Msg("response body close")
73 - }
74 - }()
75 -
76 - var payload Hosts
77 - if err := json.NewDecoder(resp.Body).Decode(&payload); err != nil {
78 - return nil, err
79 - }
80 - addrs := make([]string, 0, len(payload.ServerAddrs))
81 - for _, s := range payload.ServerAddrs {
82 - // sanity check
83 - if strings.Contains(s, "/p2p/") && (strings.Contains(s, "/ip4/") || strings.Contains(s, "/ip6/")) {
84 - addrs = append(addrs, s)
85 - }
86 - }
87 - return addrs, nil
88 -}
relaydns/utils_test.go deleted
-18
@@ -1,18 +0,0 @@
1 -package relaydns
2 -
3 -import (
4 - "fmt"
5 - "testing"
6 - "time"
7 -
8 - "github.com/cockroachdb/crlib/testutils/require"
9 -)
10 -
11 -func TestFetchMultiAddrsFromHosts(t *testing.T) {
12 - url := "http://relaydns.gosuda.org"
13 - timeout := 5 * time.Second
14 -
15 - addrs, err := FetchMultiaddrsFromHosts(url, timeout)
16 - require.NoError(t, err)
17 - fmt.Println(addrs)
18 -}
sdk/go/README.md deleted
-53
@@ -1,53 +0,0 @@
1 -# Go SDK
2 -
3 -This SDK helps you advertise a local TCP service (e.g., HTTP) over libp2p so a RelayDNS server can discover and proxy to it.
4 -
5 -## Minimal example (HTTP backend)
6 -
7 -```go
8 -package main
9 -
10 -import (
11 - "context"
12 - "fmt"
13 - "log"
14 -
15 - sdk "github.com/gosuda/relaydns/sdk/go"
16 -)
17 -
18 -func main() {
19 - ctx := context.Background()
20 -
21 - // Assume your local HTTP server listens on 127.0.0.1:8080
22 - cli, err := sdk.NewClient(ctx, sdk.ClientConfig{
23 - Name: "example-backend",
24 - TargetTCP: "127.0.0.1:8080",
25 - ServerURL: "http://relaydns.gosuda.org",
26 - })
27 - if err != nil { log.Fatal(err) }
28 -
29 - if err := cli.Start(ctx); err != nil { log.Fatal(err) }
30 - defer func() { _ = cli.Close() }()
31 -
32 - // Blocks in your real app; here you’d run until SIGINT, etc.
33 - fmt.Println("status:", cli.ServerStatus())
34 -}
35 -```
36 -
37 -## Key concepts
38 -
39 -- `TargetTCP`: If set, inbound libp2p streams are proxied directly to the local TCP service using a bidirectional byte pipe.
40 -- `ServerURL`: If set, the client periodically fetches multiaddrs from `/hosts` and attempts to connect to the server’s peer; `ServerStatus()` reports `Connected` only when libp2p connectivity is established.
41 -- Defaults: Reasonable defaults are applied (protocol/topic, advertise intervals, reasonable HTTP timeout, and address sorting that prefers QUIC and local addresses).
42 -
43 -## Lifecycle
44 -
45 -- `NewClient` creates the libp2p host and applies defaults.
46 -- `Start` installs the stream handler, joins pubsub, begins advertising, and starts background refresh (if `ServerURL` is set).
47 -- `Close` stops background goroutines, removes the handler, and closes the host.
48 -
49 -See working examples under `sdk/go/examples/`:
50 -
51 -- `http-client`: simple HTTP backend with a status page.
52 -- `chat`: WebSocket chat demo; demonstrates HTTP upgrade tunneling.
53 -
sdk/go/client.go deleted
-364
@@ -1,364 +0,0 @@
1 -package sdk
2 -
3 -import (
4 - "context"
5 - "encoding/json"
6 - "fmt"
7 - "io"
8 - "net"
9 - "sync"
10 - "time"
11 -
12 - pubsub "github.com/libp2p/go-libp2p-pubsub"
13 - "github.com/libp2p/go-libp2p/core/host"
14 - "github.com/libp2p/go-libp2p/core/network"
15 - "github.com/libp2p/go-libp2p/core/peer"
16 - "github.com/libp2p/go-libp2p/core/protocol"
17 - ma "github.com/multiformats/go-multiaddr"
18 - "github.com/rs/zerolog/log"
19 -
20 - "github.com/gosuda/relaydns/relaydns"
21 -)
22 -
23 -// ClientConfig configures the client. Defaults apply; set Handler or TargetTCP.
24 -type ClientConfig struct {
25 - ServerURL string
26 - Bootstraps []string
27 - HTTPTimeout time.Duration
28 - PreferQUIC bool
29 - PreferLocal bool
30 -
31 - // Protocol (e.g. "/relaydns/http/1.0"); Topic for adverts.
32 - Protocol string
33 - Topic string
34 -
35 - AdvertiseEvery time.Duration
36 - AdvertiseTTL time.Duration
37 - RefreshBootstrapsEvery time.Duration
38 -
39 - Name string
40 - DNS string
41 -
42 - // Set one: custom stream Handler, or TargetTCP to proxy bytes to a local TCP service.
43 - Handler func(s network.Stream)
44 - TargetTCP string
45 -}
46 -
47 -// RelayClient advertises over pubsub and handles inbound streams.
48 -type RelayClient struct {
49 - h host.Host
50 - cfg ClientConfig
51 - protoID protocol.ID
52 -
53 - ps *pubsub.PubSub
54 - t *pubsub.Topic
55 - wg sync.WaitGroup
56 - stop context.CancelFunc
57 -
58 - statusMu sync.RWMutex
59 - serverHealthy bool
60 -}
61 -
62 -// sensible defaults for optional client config
63 -const (
64 - defaultAdvertiseEvery = 5 * time.Second
65 - defaultHTTPTimeout = 3 * time.Second
66 - defaultRefreshBootstraps = 20 * time.Second
67 -)
68 -
69 -// applyDefaults fills zero-values in cfg with sane defaults.
70 -func applyDefaults(cfg ClientConfig) ClientConfig {
71 - if cfg.AdvertiseEvery <= 0 {
72 - cfg.AdvertiseEvery = defaultAdvertiseEvery
73 - }
74 - if cfg.AdvertiseTTL <= 0 {
75 - // Reduce default TTL from 50s to 15s (3x default advertise interval)
76 - cfg.AdvertiseTTL = 3 * cfg.AdvertiseEvery
77 - }
78 - if cfg.HTTPTimeout <= 0 {
79 - cfg.HTTPTimeout = defaultHTTPTimeout
80 - }
81 - if cfg.RefreshBootstrapsEvery <= 0 {
82 - cfg.RefreshBootstrapsEvery = defaultRefreshBootstraps
83 - }
84 - // Always prefer QUIC and local addresses for better performance and locality.
85 - cfg.PreferQUIC = true
86 - cfg.PreferLocal = true
87 - if cfg.Protocol == "" {
88 - cfg.Protocol = relaydns.DefaultProtocol
89 - }
90 - if cfg.Topic == "" {
91 - cfg.Topic = relaydns.DefaultTopic
92 - }
93 - return cfg
94 -}
95 -
96 -// NewClient creates a client (not started) with defaults applied.
97 -func NewClient(ctx context.Context, cfg ClientConfig) (*RelayClient, error) {
98 - cfg = applyDefaults(cfg)
99 -
100 - h, err := relaydns.MakeHost(ctx, 0, true)
101 - if err != nil {
102 - return nil, fmt.Errorf("make host: %w", err)
103 - }
104 - b := &RelayClient{
105 - h: h,
106 - cfg: cfg,
107 - protoID: protocol.ID(cfg.Protocol),
108 - }
109 - return b, nil
110 -}
111 -
112 -// Start wires handlers, joins pubsub, advertises, and refreshes bootstraps.
113 -func (b *RelayClient) Start(ctx context.Context) error {
114 - if b.stop != nil {
115 - return fmt.Errorf("client already started")
116 - }
117 - // 1) resolve bootstraps (flags + optional server health)
118 - boot := b.resolveBootstraps()
119 - if len(boot) > 0 {
120 - relaydns.ConnectBootstraps(ctx, b.h, boot)
121 - // If a server URL is configured, only mark healthy if actually
122 - // connected to the server peer (not just able to fetch /hosts).
123 - if b.cfg.ServerURL != "" {
124 - if addrs, err := relaydns.FetchMultiaddrsFromHosts(b.cfg.ServerURL, b.cfg.HTTPTimeout); err == nil {
125 - if pid, ok := serverPeerFromAddrs(addrs); ok {
126 - if b.h.Network().Connectedness(pid) == network.Connected {
127 - b.setServerHealthy(true)
128 - } else {
129 - b.setServerHealthy(false)
130 - }
131 - }
132 - }
133 - }
134 - } else {
135 - log.Warn().Msg("relaydns: no bootstrap sources provided (Bootstraps/ServerURL); discovery may fail")
136 - }
137 -
138 - // 2) stream handler for inbound libp2p streams
139 - if err := b.setupStreamHandler(); err != nil {
140 - return err
141 - }
142 -
143 - // 3) pubsub join (for adverts)
144 - if err := b.joinPubSub(ctx); err != nil {
145 - return err
146 - }
147 -
148 - // 4) advertiser loop
149 - advCtx, cancel := context.WithCancel(ctx)
150 - b.stop = cancel
151 - b.startAdvertiser(advCtx)
152 -
153 - // 5) background: periodically re-fetch bootstraps from server and reconnect
154 - if b.cfg.ServerURL != "" {
155 - b.startRefreshLoop(advCtx)
156 - }
157 -
158 - if addrs := relaydns.BuildAddrs(b.Host()); len(addrs) > 0 {
159 - for _, s := range addrs {
160 - log.Info().Msgf("[client] host addr: %s", s)
161 - }
162 - } else {
163 - log.Info().Msgf("[client] host peer: %s (no listen addrs yet)", b.Host().ID().String())
164 - }
165 -
166 - return nil
167 -}
168 -
169 -func (b *RelayClient) Host() host.Host {
170 - return b.h
171 -}
172 -
173 -// Close stops all loops, removes the handler, and closes the host.
174 -func (b *RelayClient) Close() error {
175 - if b.stop != nil {
176 - b.stop()
177 - }
178 - b.wg.Wait()
179 - if b.t != nil {
180 - _ = b.t.Close()
181 - }
182 - if b.h != nil {
183 - if b.protoID != "" {
184 - b.h.RemoveStreamHandler(b.protoID)
185 - }
186 - return b.h.Close()
187 - }
188 - return nil
189 -}
190 -
191 -func (b *RelayClient) setServerHealthy(ok bool) {
192 - b.statusMu.Lock()
193 - b.serverHealthy = ok
194 - b.statusMu.Unlock()
195 -}
196 -
197 -// resolveBootstraps merges configured bootstraps with optional server-provided
198 -// multiaddrs from /health. It updates serverHealthy accordingly.
199 -func (b *RelayClient) resolveBootstraps() []string {
200 - boot := make([]string, 0, len(b.cfg.Bootstraps)+4)
201 - if len(b.cfg.Bootstraps) > 0 {
202 - boot = append(boot, b.cfg.Bootstraps...)
203 - }
204 - if b.cfg.ServerURL != "" {
205 - if addrs, err := relaydns.FetchMultiaddrsFromHosts(b.cfg.ServerURL, b.cfg.HTTPTimeout); err != nil {
206 - b.setServerHealthy(false)
207 - log.Warn().Err(err).Msgf("relaydns: fetch /hosts from %s failed", b.cfg.ServerURL)
208 - } else {
209 - // Do not mark healthy yet; only after verifying libp2p connectivity
210 - relaydns.SortMultiaddrs(addrs, b.cfg.PreferQUIC, b.cfg.PreferLocal)
211 - boot = append(boot, addrs...)
212 - }
213 - }
214 - return relaydns.RemoveDuplicate(boot)
215 -}
216 -
217 -// setupStreamHandler installs the handler. TargetTCP proxies stream <-> local TCP.
218 -func (b *RelayClient) setupStreamHandler() error {
219 - switch {
220 - case b.cfg.Handler != nil:
221 - b.h.SetStreamHandler(b.protoID, b.cfg.Handler)
222 - case b.cfg.TargetTCP != "":
223 - b.h.SetStreamHandler(b.protoID, func(s network.Stream) {
224 - stream := s
225 - backendAddr := b.cfg.TargetTCP
226 - defer func() {
227 - if err := stream.Close(); err != nil {
228 - log.Debug().Err(err).Msg("relaydns: stream close")
229 - }
230 - }()
231 -
232 - backendConn, err := net.Dial("tcp", backendAddr)
233 - if err != nil {
234 - log.Error().Err(err).Msgf("relaydns: dial %s", backendAddr)
235 - return
236 - }
237 - defer func() {
238 - if err := backendConn.Close(); err != nil {
239 - log.Debug().Err(err).Msg("relaydns: conn close")
240 - }
241 - }()
242 -
243 - var wg sync.WaitGroup
244 - wg.Add(2)
245 - go func() { defer wg.Done(); _, _ = io.Copy(backendConn, stream) }()
246 - go func() { defer wg.Done(); _, _ = io.Copy(stream, backendConn) }()
247 - wg.Wait()
248 - })
249 - default:
250 - return fmt.Errorf("relaydns: either Handler or TargetTCP must be set")
251 - }
252 - return nil
253 -}
254 -
255 -// joinPubSub creates a GossipSub instance and joins the advert topic.
256 -func (b *RelayClient) joinPubSub(ctx context.Context) error {
257 - ps, err := pubsub.NewGossipSub(ctx, b.h, pubsub.WithMessageSigning(true))
258 - if err != nil {
259 - return err
260 - }
261 - t, err := ps.Join(b.cfg.Topic)
262 - if err != nil {
263 - return err
264 - }
265 - b.ps, b.t = ps, t
266 - return nil
267 -}
268 -
269 -// startAdvertiser periodically publishes Advertise messages with host addrs.
270 -func (b *RelayClient) startAdvertiser(ctx context.Context) {
271 - b.wg.Add(1)
272 - go func() {
273 - defer b.wg.Done()
274 - ticker := time.NewTicker(b.cfg.AdvertiseEvery)
275 - defer ticker.Stop()
276 - for {
277 - select {
278 - case <-ctx.Done():
279 - return
280 - case <-ticker.C:
281 - enc := relaydns.BuildAddrs(b.h)
282 - ad := relaydns.Advertise{
283 - Peer: b.h.ID().String(),
284 - Name: b.cfg.Name,
285 - DNS: b.cfg.DNS,
286 - Addrs: enc,
287 - Ready: true,
288 - Load: 0.0,
289 - TS: time.Now().UTC(),
290 - TTL: int(b.cfg.AdvertiseTTL.Seconds()),
291 - Proto: string(b.protoID),
292 - }
293 - payload, _ := json.Marshal(ad)
294 - _ = b.t.Publish(ctx, payload)
295 - }
296 - }
297 - }()
298 -}
299 -
300 -// startRefreshLoop periodically fetches /health and attempts (re)connects.
301 -func (b *RelayClient) startRefreshLoop(ctx context.Context) {
302 - b.wg.Add(1)
303 - go func() {
304 - defer b.wg.Done()
305 - t := time.NewTicker(b.cfg.RefreshBootstrapsEvery)
306 - defer t.Stop()
307 - for {
308 - select {
309 - case <-ctx.Done():
310 - return
311 - case <-t.C:
312 - addrs, err := relaydns.FetchMultiaddrsFromHosts(b.cfg.ServerURL, b.cfg.HTTPTimeout)
313 - if err != nil {
314 - b.setServerHealthy(false)
315 - log.Warn().Err(err).Msgf("refresh /hosts from %s failed", b.cfg.ServerURL)
316 - continue
317 - }
318 - relaydns.SortMultiaddrs(addrs, b.cfg.PreferQUIC, b.cfg.PreferLocal)
319 - addrs = relaydns.RemoveDuplicate(addrs)
320 - if len(addrs) > 0 {
321 - // Always attempt (re)connect; ConnectBootstraps handles dedupe and quiet logging
322 - relaydns.ConnectBootstraps(ctx, b.h, addrs)
323 - // Only mark healthy if actually connected to server peer
324 - if pid, ok := serverPeerFromAddrs(addrs); ok {
325 - if b.h.Network().Connectedness(pid) == network.Connected {
326 - b.setServerHealthy(true)
327 - } else {
328 - b.setServerHealthy(false)
329 - }
330 - }
331 - }
332 - }
333 - }
334 - }()
335 -}
336 -
337 -// serverPeerFromAddrs extracts the first peer.ID found in the provided
338 -// multiaddrs. The server advertises its own addrs including /p2p/<peer>.
339 -func serverPeerFromAddrs(addrs []string) (peer.ID, bool) {
340 - for _, s := range addrs {
341 - m, err := ma.NewMultiaddr(s)
342 - if err != nil {
343 - continue
344 - }
345 - if ai, err := peer.AddrInfoFromP2pAddr(m); err == nil {
346 - return ai.ID, true
347 - }
348 - }
349 - return "", false
350 -}
351 -
352 -// ServerStatus returns "Connected", "Connecting...", or "N/A".
353 -func (b *RelayClient) ServerStatus() string {
354 - if b.cfg.ServerURL == "" {
355 - return "N/A"
356 - }
357 - b.statusMu.RLock()
358 - ok := b.serverHealthy
359 - b.statusMu.RUnlock()
360 - if ok {
361 - return "Connected"
362 - }
363 - return "Connecting..."
364 -}
sdk/go/e2ee.go deleted
-105
@@ -1,105 +0,0 @@
1 -package sdk
2 -
3 -import (
4 - "crypto/aes"
5 - "crypto/cipher"
6 - crand "crypto/rand"
7 - "crypto/sha256"
8 - "encoding/base64"
9 - "errors"
10 - "os"
11 - "path/filepath"
12 - "strings"
13 -
14 - "golang.org/x/crypto/pbkdf2"
15 -)
16 -
17 -// Envelope is a simple password-derived AES-GCM container used by examples.
18 -// Fields are base64-encoded to keep the JSON compact and interoperable with browser JS.
19 -type Envelope struct {
20 - Salt string `json:"salt"`
21 - Nonce string `json:"nonce"`
22 - Ct string `json:"ct"`
23 -}
24 -
25 -// EnsurePSKAtPath loads a pre-shared key (PSK) from the given file path.
26 -// If missing/empty, generates a random base64url string, writes it, and returns it.
27 -func EnsurePSKAtPath(path string) (string, error) {
28 - if data, err := os.ReadFile(path); err == nil {
29 - if s := strings.TrimSpace(string(data)); s != "" {
30 - return s, nil
31 - }
32 - }
33 - if err := os.MkdirAll(filepath.Dir(path), 0o700); err != nil {
34 - return "", err
35 - }
36 - buf := make([]byte, 16)
37 - if _, err := crand.Read(buf); err != nil {
38 - return "", err
39 - }
40 - psk := base64.RawURLEncoding.EncodeToString(buf)
41 - if err := os.WriteFile(path, []byte(psk+"\n"), 0o600); err != nil {
42 - return "", err
43 - }
44 - return psk, nil
45 -}
46 -
47 -func deriveKey(psk string, salt []byte) []byte {
48 - return pbkdf2.Key([]byte(psk), salt, 100000, 32, sha256.New)
49 -}
50 -
51 -// DecryptEnvelope decrypts the given envelope using a key derived from psk+salt.
52 -func DecryptEnvelope(psk string, env Envelope) ([]byte, error) {
53 - salt, err := base64.StdEncoding.DecodeString(env.Salt)
54 - if err != nil {
55 - return nil, err
56 - }
57 - nonce, err := base64.StdEncoding.DecodeString(env.Nonce)
58 - if err != nil {
59 - return nil, err
60 - }
61 - ct, err := base64.StdEncoding.DecodeString(env.Ct)
62 - if err != nil {
63 - return nil, err
64 - }
65 - if len(nonce) != 12 {
66 - return nil, errors.New("bad nonce")
67 - }
68 - key := deriveKey(psk, salt)
69 - block, err := aes.NewCipher(key)
70 - if err != nil {
71 - return nil, err
72 - }
73 - aead, err := cipher.NewGCM(block)
74 - if err != nil {
75 - return nil, err
76 - }
77 - return aead.Open(nil, nonce, ct, nil)
78 -}
79 -
80 -// EncryptEnvelope encrypts pt with a key derived from psk and a fresh random salt/nonce.
81 -func EncryptEnvelope(psk string, pt []byte) (Envelope, error) {
82 - var env Envelope
83 - salt := make([]byte, 16)
84 - if _, err := crand.Read(salt); err != nil {
85 - return env, err
86 - }
87 - nonce := make([]byte, 12)
88 - if _, err := crand.Read(nonce); err != nil {
89 - return env, err
90 - }
91 - key := deriveKey(psk, salt)
92 - block, err := aes.NewCipher(key)
93 - if err != nil {
94 - return env, err
95 - }
96 - aead, err := cipher.NewGCM(block)
97 - if err != nil {
98 - return env, err
99 - }
100 - ct := aead.Seal(nil, nonce, pt, nil)
101 - env.Salt = base64.StdEncoding.EncodeToString(salt)
102 - env.Nonce = base64.StdEncoding.EncodeToString(nonce)
103 - env.Ct = base64.StdEncoding.EncodeToString(ct)
104 - return env, nil
105 -}
sdk/go/examples/chat/main.go deleted
-127
@@ -1,127 +0,0 @@
1 -package main
2 -
3 -import (
4 - "context"
5 - "fmt"
6 - "net"
7 - "net/http"
8 - "os"
9 - "os/signal"
10 - "syscall"
11 - "time"
12 -
13 - "github.com/rs/zerolog/log"
14 - "github.com/spf13/cobra"
15 -
16 - sdk "github.com/gosuda/relaydns/sdk/go"
17 -)
18 -
19 -var rootCmd = &cobra.Command{
20 - Use: "relaydns-chat",
21 - Short: "RelayDNS demo chat (local HTTP backend + libp2p advertiser)",
22 - RunE: runChat,
23 -}
24 -
25 -var (
26 - flagServerURL string
27 - flagPort int
28 - flagName string
29 - flagDataPath string
30 -)
31 -
32 -func init() {
33 - flags := rootCmd.PersistentFlags()
34 - flags.StringVar(&flagServerURL, "server-url", "http://relaydns.gosuda.org", "relayserver base URL to auto-fetch multiaddrs from /health")
35 - flags.IntVar(&flagPort, "port", 8091, "local chat HTTP port")
36 - flags.StringVar(&flagName, "name", "example-chat", "backend display name")
37 - flags.StringVar(&flagDataPath, "data-path", "", "optional directory to persist chat history via PebbleDB")
38 -}
39 -
40 -func main() {
41 - if err := rootCmd.Execute(); err != nil {
42 - log.Fatal().Err(err).Msg("execute chat command")
43 - }
44 -}
45 -
46 -func runChat(cmd *cobra.Command, args []string) error {
47 - ctx, cancel := context.WithCancel(context.Background())
48 - defer cancel() // Ensure context is cancelled on all exit paths
49 -
50 - // 1) start local chat HTTP backend
51 - httpLn, err := net.Listen("tcp", fmt.Sprintf(":%d", flagPort))
52 - if err != nil {
53 - return fmt.Errorf("listen chat: %w", err)
54 - }
55 - hub := newHub()
56 -
57 - // Optional: open persistent store and preload history
58 - var store *messageStore
59 - if flagDataPath != "" {
60 - s, err := openMessageStore(flagDataPath)
61 - if err != nil {
62 - log.Warn().Err(err).Msg("[chat] open store failed; running in memory only")
63 - } else {
64 - store = s
65 - if msgs, err := store.LoadAll(); err != nil {
66 - log.Warn().Err(err).Msg("[chat] load history failed")
67 - } else if len(msgs) > 0 {
68 - hub.bootstrap(msgs)
69 - log.Info().Msgf("[chat] loaded %d messages from store", len(msgs))
70 - }
71 - hub.attachStore(store)
72 - }
73 - }
74 - // Build router and run server in main
75 - handler := NewHandler(flagName, hub)
76 - httpSrv := &http.Server{Handler: handler, ReadHeaderTimeout: 5 * time.Second, IdleTimeout: 60 * time.Second}
77 - go func() {
78 - if err := httpSrv.Serve(httpLn); err != nil && err != http.ErrServerClosed {
79 - log.Error().Err(err).Msg("chat http error")
80 - }
81 - }()
82 -
83 - // 2) advertise over RelayDNS (HTTP tunneled via server /peer route)
84 - client, err := sdk.NewClient(ctx, sdk.ClientConfig{
85 - Name: flagName,
86 - TargetTCP: fmt.Sprintf("127.0.0.1:%d", flagPort),
87 - ServerURL: flagServerURL,
88 - })
89 - if err != nil {
90 - return fmt.Errorf("new client: %w", err)
91 - }
92 - if err := client.Start(ctx); err != nil {
93 - return fmt.Errorf("start client: %w", err)
94 - }
95 -
96 - sig := make(chan os.Signal, 1)
97 - signal.Notify(sig, syscall.SIGINT, syscall.SIGTERM)
98 - <-sig
99 - log.Info().Msg("[chat] shutting down...")
100 -
101 - // Shutdown sequence:
102 - // 1. Close client (waits for goroutines, closes libp2p host)
103 - if err := client.Close(); err != nil {
104 - log.Warn().Err(err).Msg("[chat] client close error")
105 - }
106 -
107 - // 2. Shutdown HTTP server with a fresh context (with timeout)
108 - shutdownCtx, shutdownCancel := context.WithTimeout(context.Background(), 5*time.Second)
109 - defer shutdownCancel()
110 - if err := httpSrv.Shutdown(shutdownCtx); err != nil {
111 - log.Error().Err(err).Msg("[chat] http server shutdown error")
112 - }
113 -
114 - // 3. Close all websocket connections and wait for handlers to finish
115 - hub.closeAll()
116 - hub.wait()
117 -
118 - // 4. Close persistent store if opened
119 - if store != nil {
120 - if err := store.Close(); err != nil {
121 - log.Warn().Err(err).Msg("[chat] store close error")
122 - }
123 - }
124 -
125 - log.Info().Msg("[chat] shutdown complete")
126 - return nil
127 -}
sdk/go/examples/chat/persist.go deleted
-86
@@ -1,86 +0,0 @@
1 -package main
2 -
3 -import (
4 - "encoding/binary"
5 - "encoding/json"
6 - "os"
7 - "path/filepath"
8 - "sync"
9 -
10 - "github.com/cockroachdb/pebble"
11 -)
12 -
13 -// messageStore persists chat messages in a PebbleDB key-value store.
14 -// Keys are 8-byte big-endian sequence numbers increasing monotonically.
15 -type messageStore struct {
16 - db *pebble.DB
17 - mu sync.Mutex
18 - next uint64
19 -}
20 -
21 -func openMessageStore(dir string) (*messageStore, error) {
22 - if dir == "" {
23 - return nil, nil
24 - }
25 - if err := os.MkdirAll(dir, 0o755); err != nil {
26 - return nil, err
27 - }
28 - // Pebble database lives directly at the provided directory.
29 - // Accept default options for simplicity.
30 - db, err := pebble.Open(filepath.Clean(dir), &pebble.Options{})
31 - if err != nil {
32 - return nil, err
33 - }
34 - s := &messageStore{db: db}
35 - // Discover next sequence by reading the last key.
36 - it, err := db.NewIter(nil)
37 - if err != nil {
38 - return nil, err
39 - }
40 - defer func() { _ = it.Close() }()
41 - if it.Last() {
42 - if len(it.Key()) >= 8 {
43 - s.next = binary.BigEndian.Uint64(it.Key()[:8]) + 1
44 - }
45 - }
46 - return s, nil
47 -}
48 -
49 -func (s *messageStore) Append(m message) error {
50 - if s == nil || s.db == nil {
51 - return nil
52 - }
53 - s.mu.Lock()
54 - defer s.mu.Unlock()
55 - key := make([]byte, 8)
56 - binary.BigEndian.PutUint64(key, s.next)
57 - s.next++
58 - val, _ := json.Marshal(m)
59 - return s.db.Set(key, val, pebble.Sync)
60 -}
61 -
62 -func (s *messageStore) LoadAll() ([]message, error) {
63 - if s == nil || s.db == nil {
64 - return nil, nil
65 - }
66 - it, err := s.db.NewIter(nil)
67 - if err != nil {
68 - return nil, err
69 - }
70 - defer func() { _ = it.Close() }()
71 - out := make([]message, 0, 256)
72 - for it.First(); it.Valid(); it.Next() {
73 - var m message
74 - if err := json.Unmarshal(it.Value(), &m); err == nil {
75 - out = append(out, m)
76 - }
77 - }
78 - return out, nil
79 -}
80 -
81 -func (s *messageStore) Close() error {
82 - if s == nil || s.db == nil {
83 - return nil
84 - }
85 - return s.db.Close()
86 -}
sdk/go/examples/chat/view.go deleted
-470
@@ -1,470 +0,0 @@
1 -package main
2 -
3 -import (
4 - "html/template"
5 - "net/http"
6 - "sort"
7 - "strconv"
8 - "sync"
9 - "time"
10 -
11 - "github.com/go-chi/chi/v5"
12 - "github.com/gorilla/websocket"
13 - "github.com/rs/zerolog/log"
14 -)
15 -
16 -// simple in-memory chat hub
17 -type hub struct {
18 - mu sync.RWMutex
19 - messages []message
20 - conns map[*websocket.Conn]struct{}
21 - connUID map[*websocket.Conn]string
22 - userConns map[string]map[*websocket.Conn]struct{}
23 - userName map[string]string
24 - wg sync.WaitGroup
25 - store *messageStore
26 -}
27 -
28 -type message struct {
29 - TS time.Time `json:"ts"`
30 - User string `json:"user"`
31 - Text string `json:"text"`
32 - Event string `json:"event,omitempty"` // "joined" | "left" | "roster"
33 - UID string `json:"uid,omitempty"`
34 - Users []string `json:"users,omitempty"`
35 -}
36 -
37 -func newHub() *hub {
38 - return &hub{
39 - conns: map[*websocket.Conn]struct{}{},
40 - connUID: map[*websocket.Conn]string{},
41 - userConns: map[string]map[*websocket.Conn]struct{}{},
42 - userName: map[string]string{},
43 - messages: make([]message, 0, 64),
44 - }
45 -}
46 -
47 -func (h *hub) broadcast(m message) {
48 - h.mu.Lock()
49 - // Do not persist/retain roster messages in backlog; they are ephemeral UI state
50 - if m.Event != "roster" {
51 - h.messages = append(h.messages, m)
52 - }
53 - conns := make([]*websocket.Conn, 0, len(h.conns))
54 - for c := range h.conns {
55 - conns = append(conns, c)
56 - }
57 - h.mu.Unlock()
58 - if h.store != nil && m.Event != "roster" {
59 - if err := h.store.Append(m); err != nil {
60 - log.Debug().Err(err).Msg("persist message")
61 - }
62 - }
63 - for _, c := range conns {
64 - _ = c.WriteJSON(m)
65 - }
66 -}
67 -
68 -// broadcastRoster sends the current list of connected user names to all clients.
69 -func (h *hub) broadcastRoster() {
70 - // Build roster snapshot
71 - h.mu.RLock()
72 - users := make([]string, 0, len(h.userName))
73 - for uid, name := range h.userName {
74 - if set, ok := h.userConns[uid]; !ok || len(set) == 0 {
75 - continue
76 - }
77 - if name == "" {
78 - name = "anon"
79 - }
80 - users = append(users, name)
81 - }
82 - h.mu.RUnlock()
83 - // Sort for stable UI order
84 - sort.Strings(users)
85 - h.broadcast(message{TS: time.Now().UTC(), Event: "roster", Users: users})
86 -}
87 -
88 -// attachStore connects a persistent store to the hub.
89 -func (h *hub) attachStore(s *messageStore) {
90 - h.mu.Lock()
91 - h.store = s
92 - h.mu.Unlock()
93 -}
94 -
95 -// bootstrap preloads history into the in-memory buffer.
96 -func (h *hub) bootstrap(msgs []message) {
97 - h.mu.Lock()
98 - h.messages = append(h.messages, msgs...)
99 - h.mu.Unlock()
100 -}
101 -
102 -// closeAll force-closes all active websocket connections (used during shutdown).
103 -func (h *hub) closeAll() {
104 - h.mu.Lock()
105 - conns := make([]*websocket.Conn, 0, len(h.conns))
106 - for c := range h.conns {
107 - conns = append(conns, c)
108 - }
109 - h.mu.Unlock()
110 - for _, c := range conns {
111 - _ = c.WriteMessage(websocket.CloseMessage, websocket.FormatCloseMessage(websocket.CloseGoingAway, "server shutdown"))
112 - }
113 -}
114 -
115 -// wait blocks until all websocket handler goroutines have finished.
116 -func (h *hub) wait() {
117 - h.wg.Wait()
118 -}
119 -
120 -func handleWS(w http.ResponseWriter, r *http.Request, h *hub) {
121 - upgrader := websocket.Upgrader{
122 - CheckOrigin: func(r *http.Request) bool { return true },
123 - }
124 - conn, err := upgrader.Upgrade(w, r, nil)
125 - if err != nil {
126 - return
127 - }
128 - h.mu.Lock()
129 - h.conns[conn] = struct{}{}
130 - backlog := append([]message(nil), h.messages...)
131 - h.mu.Unlock()
132 -
133 - for _, m := range backlog {
134 - _ = conn.WriteJSON(m)
135 - }
136 - h.wg.Add(1)
137 - go func() {
138 - defer func() {
139 - var leftUser string
140 - var uid string
141 - var lastConn bool
142 - h.mu.Lock()
143 - uid = h.connUID[conn]
144 - if uid != "" {
145 - if set, ok := h.userConns[uid]; ok {
146 - delete(set, conn)
147 - if len(set) == 0 {
148 - lastConn = true
149 - delete(h.userConns, uid)
150 - } else {
151 - h.userConns[uid] = set
152 - }
153 - }
154 - leftUser = h.userName[uid]
155 - if lastConn {
156 - delete(h.userName, uid)
157 - }
158 - delete(h.connUID, conn)
159 - }
160 - delete(h.conns, conn)
161 - h.mu.Unlock()
162 - if leftUser != "" && lastConn {
163 - h.broadcast(message{TS: time.Now().UTC(), User: leftUser, Event: "left"})
164 - h.broadcastRoster()
165 - }
166 - _ = conn.WriteMessage(websocket.CloseMessage, websocket.FormatCloseMessage(websocket.CloseNormalClosure, ""))
167 - h.wg.Done()
168 - }()
169 - for {
170 - var req struct {
171 - User string `json:"user"`
172 - Text string `json:"text"`
173 - UID string `json:"uid"`
174 - }
175 - if err := conn.ReadJSON(&req); err != nil {
176 - return
177 - }
178 - if req.User == "" {
179 - req.User = "anon"
180 - }
181 - if req.UID == "" {
182 - // Fallback to a per-connection unique id if client didn't provide one
183 - req.UID = strconv.FormatInt(time.Now().UnixNano(), 10)
184 - }
185 - // map connection to uid and maintain per-user state
186 - var announce bool
187 - var renamed bool
188 - var prevName string
189 - h.mu.Lock()
190 - if _, ok := h.connUID[conn]; !ok {
191 - h.connUID[conn] = req.UID
192 - if _, ok := h.userConns[req.UID]; !ok {
193 - h.userConns[req.UID] = map[*websocket.Conn]struct{}{}
194 - }
195 - if len(h.userConns[req.UID]) == 0 {
196 - announce = true
197 - }
198 - h.userConns[req.UID][conn] = struct{}{}
199 - }
200 - if cur, ok := h.userName[req.UID]; !ok {
201 - h.userName[req.UID] = req.User
202 - } else if cur != req.User {
203 - prevName = cur
204 - h.userName[req.UID] = req.User
205 - renamed = true
206 - }
207 - h.mu.Unlock()
208 - if announce {
209 - h.broadcast(message{TS: time.Now().UTC(), User: req.User, Event: "joined"})
210 - h.broadcastRoster()
211 - } else if renamed {
212 - // Announce rename as an event line in chat
213 - h.broadcast(message{TS: time.Now().UTC(), User: prevName, Text: req.User, Event: "rename"})
214 - h.broadcastRoster()
215 - }
216 - if req.Text == "" {
217 - continue
218 - }
219 - h.broadcast(message{TS: time.Now().UTC(), User: req.User, Text: req.Text})
220 - }
221 - }()
222 -}
223 -
224 -func serveIndex(w http.ResponseWriter, r *http.Request, name string) {
225 - w.Header().Set("Content-Type", "text/html; charset=utf-8")
226 - _ = indexTmpl.Execute(w, struct{ Name string }{Name: name})
227 -}
228 -
229 -// serveChatHTTP starts serving the chat UI and websocket endpoint and returns the server.
230 -// Callers are responsible for shutting it down via Server.Shutdown.
231 -// NewHandler builds the chat HTTP router (UI + websocket)
232 -func NewHandler(name string, h *hub) http.Handler {
233 - r := chi.NewRouter()
234 - r.Get("/", func(w http.ResponseWriter, r *http.Request) { serveIndex(w, r, name) })
235 - r.Get("/ws", func(w http.ResponseWriter, r *http.Request) { handleWS(w, r, h) })
236 - return r
237 -}
238 -
239 -var indexTmpl = template.Must(template.New("chat").Parse(`<!DOCTYPE html>
240 -<html lang="en">
241 -<head>
242 - <meta charset="utf-8" />
243 - <meta name="viewport" content="width=device-width, initial-scale=1" />
244 - <title>RelayDNS Chat — {{.Name}}</title>
245 - <style>
246 - :root{
247 - --bg: #0d1117;
248 - --panel: #111827;
249 - --border: #1f2937;
250 - --fg: #e5e7eb;
251 - --muted: #9ca3af;
252 - --accent: #22c55e;
253 - --cursor: #22c55e;
254 - }
255 - *{ box-sizing: border-box }
256 - /* Prefer locally-installed D2Coding for Korean monospaced rendering */
257 - @font-face { font-family: 'D2Coding'; src: local('D2Coding'), local('D2Coding Ligature'), local('D2Coding Nerd'); font-display: swap; }
258 - body { margin:0; padding:24px; background:var(--bg); color:var(--fg); font-family: ui-sans-serif, system-ui, -apple-system, Segoe UI, Roboto, Helvetica, Arial }
259 - .wrap { max-width: 920px; margin: 0 auto }
260 - h1 { margin:0 0 12px 0; font-weight:700 }
261 - .term { border:1px solid var(--border); border-radius:10px; background:var(--panel); overflow:hidden; position: relative }
262 - .termbar { display:flex; align-items:center; justify-content:space-between; padding:10px 12px; border-bottom:1px solid var(--border); font-family: 'D2Coding', ui-monospace, SFMono-Regular, Menlo, Consolas, monospace; font-size:14px }
263 - .termbar-left { display:flex; align-items:center; gap:8px }
264 - .termbar-center { flex:1 1 auto; display:flex; justify-content:center }
265 - .term-actions { display:flex; align-items:center; gap:8px }
266 - .dots { display:flex; gap:6px }
267 - .dot { width:10px; height:10px; border-radius:50%; }
268 - .dot.red{ background:#ef4444 }
269 - .dot.yellow{ background:#f59e0b }
270 - .dot.green{ background:#22c55e }
271 - .nick { display:flex; align-items:center; gap:8px }
272 - .nick input{ background:transparent; border:1px solid var(--border); color:var(--fg); padding:6px 8px; border-radius:6px; font-family:inherit; font-size:13px; width:180px }
273 - .nick button{ background:transparent; border:1px solid var(--border); color:var(--fg); padding:6px 8px; border-radius:6px; font-family:inherit; font-size:13px; cursor:pointer }
274 - .screen { height:420px; overflow:auto; padding:14px; font-family: 'D2Coding', ui-monospace, SFMono-Regular, Menlo, Consolas, monospace; font-size:14px; line-height:1.5; }
275 - .line { white-space: pre-wrap; word-break: break-word }
276 - .ts { color:var(--muted) }
277 - .usr { color:#60a5fa }
278 - .event { color: var(--muted) }
279 - .event .usr { color: var(--muted) }
280 - .promptline { display:flex; align-items:center; gap:8px; padding:12px 14px; border-top:1px solid var(--border); font-family: 'D2Coding', ui-monospace, SFMono-Regular, Menlo, Consolas, monospace; }
281 - #prompt { color:var(--accent) }
282 - #cmd { flex:1 1 auto; min-width:0; background:transparent; border:none; outline:none; color:var(--fg); font-family: inherit; font-size:14px; caret-color: var(--cursor) }
283 - small{ color:var(--muted); display:block; margin-top:10px }
284 -
285 - /* Scrollbar styling for log and users list */
286 - .screen { scrollbar-width: thin; scrollbar-color: #374151 #0d1117; }
287 - .screen::-webkit-scrollbar { width: 10px }
288 - .screen::-webkit-scrollbar-track { background: #0d1117 }
289 - .screen::-webkit-scrollbar-thumb { background: #374151; border-radius: 8px; border: 2px solid #111827 }
290 - .screen::-webkit-scrollbar-thumb:hover { background: #4b5563 }
291 - .userspill { display:inline-block; border:1px solid var(--border); padding:2px 10px; border-radius:999px; color:var(--fg); font-size:12px; opacity:.9 }
292 -
293 - /* Mobile responsiveness */
294 - @media (max-width: 640px) {
295 - body { padding: 12px; }
296 - .wrap { max-width: 100%; }
297 - h1 { font-size: 18px; }
298 - .termbar { flex-wrap: wrap; gap: 8px; }
299 - .termbar-center { order: 2; width: 100%; justify-content: center; }
300 - .promptline { flex-direction: column; align-items: stretch; gap: 10px; }
301 - #prompt { order: 1; }
302 - #cmd { order: 2; font-size: 16px; }
303 - .nick { order: 3; width: 100%; }
304 - .nick input { width: 100%; font-size: 16px; }
305 - .nick button { font-size: 16px; }
306 - .screen { height: 50vh; font-size: 13px; }
307 - .promptline { flex-wrap: nowrap; }
308 - }
309 - </style>
310 -</head>
311 -<body>
312 - <div class="wrap">
313 - <h1>🔐 Chatting — {{.Name}}</h1>
314 - <div class="term">
315 - <div class="termbar">
316 - <div class="termbar-left">
317 - <div class="dots"><span class="dot red"></span><span class="dot yellow"></span><span class="dot green"></span></div>
318 - </div>
319 - <div class="termbar-center">
320 - <div class="nick">
321 - <label for="user" style="color:var(--muted)">nickname</label>
322 - <input id="user" type="text" placeholder="anon" />
323 - <button id="roll" title="randomize nickname">🎲</button>
324 - </div>
325 - </div>
326 - <div class="term-actions"><span class="userspill"><span id="users-count">0</span> Online</span></div>
327 - </div>
328 - <div id="log" class="screen"></div>
329 - <div class="promptline">
330 - <span id="prompt"></span>
331 - <input id="cmd" type="text" autocomplete="off" spellcheck="false" placeholder="type a message and press Enter" enterkeyhint="send" inputmode="text" />
332 - </div>
333 - </div>
334 - <small>Tip: Enter to send • Nickname persists locally</small>
335 - </div>
336 - <script>
337 - const log = document.getElementById('log');
338 - const user = document.getElementById('user');
339 - const cmd = document.getElementById('cmd');
340 - const roll = document.getElementById('roll');
341 - const promptEl = document.getElementById('prompt');
342 - const usersCount = document.getElementById('users-count');
343 -
344 - function setPrompt(){
345 - const nick = (user.value || 'anon').replace(/\s+/g,'').slice(0,24) || 'anon';
346 - promptEl.textContent = nick + '@chat:~$';
347 - }
348 - function randomNick(){
349 - // Short nickname: one word + 4-digit number
350 - const words = ['gopher','rust','unix','kernel','docker','kube','vim','emacs','tmux','nvim','git','linux','bsd','wasm','grpc','lambda','pointer','monad','null','byte','packet','devops','cli'];
351 - const w = words[Math.floor(Math.random()*words.length)];
352 - const num = Math.floor(Math.random()*9000) + 1000; // 4-digit
353 - return w + '-' + num;
354 - }
355 - // Stable client UID per browser (per origin)
356 - function genUID(){ try{ return (crypto.randomUUID && crypto.randomUUID()) || '' }catch(_){ return '' } }
357 - function fallbackUID(){ return Math.random().toString(36).slice(2) + Date.now().toString(36) }
358 - let clientUID = null;
359 - try { clientUID = localStorage.getItem('relaydns_uid'); } catch(_) {}
360 - if(!clientUID || clientUID.length < 8){ clientUID = genUID() || fallbackUID(); try { localStorage.setItem('relaydns_uid', clientUID); } catch(_) {} }
361 -
362 - // Restore nickname or initialize randomly
363 - let savedNick = null;
364 - try { savedNick = localStorage.getItem('relaydns_nick'); } catch(_) {}
365 - if(savedNick){
366 - const oldPattern = /^[a-z]+-[a-z]+-[0-9a-z]{2,}$/i.test(savedNick);
367 - if (oldPattern) {
368 - user.value = randomNick();
369 - try { localStorage.setItem('relaydns_nick', user.value); } catch(_) {}
370 - } else {
371 - user.value = savedNick;
372 - }
373 - } else {
374 - user.value = randomNick();
375 - try { localStorage.setItem('relaydns_nick', user.value); } catch(_) {}
376 - }
377 - setPrompt();
378 - // Debounced notify of nickname changes to server so roster updates without sending a chat
379 - let nickTimer = null;
380 - user.addEventListener('input', () => {
381 - try{ localStorage.setItem('relaydns_nick', user.value); }catch(_){}
382 - setPrompt();
383 - if (ws && ws.readyState === 1) {
384 - if (nickTimer) clearTimeout(nickTimer);
385 - nickTimer = setTimeout(() => {
386 - try{ ws.send(JSON.stringify({ user: (user.value || 'anon'), text: '', uid: clientUID })); }catch(_){ }
387 - }, 300);
388 - }
389 - });
390 - roll.addEventListener('click', () => {
391 - user.value = randomNick();
392 - try{ localStorage.setItem('relaydns_nick', user.value); }catch(_){}
393 - setPrompt();
394 - user.focus();
395 - });
396 -
397 - // Stable color per nickname (expanded palette)
398 - const PALETTE = [
399 - '#60a5fa','#22c55e','#f59e0b','#ef4444','#a78bfa','#14b8a6','#eab308','#f472b6','#8b5cf6','#06b6d4',
400 - '#34d399','#fb7185','#c084fc','#f97316','#84cc16','#10b981','#38bdf8','#f43f5e','#e879f9','#fde047',
401 - '#93c5fd','#4ade80','#fca5a5','#a3e635','#67e8f9','#f0abfc','#fbbf24','#86efac'
402 - ];
403 - function hashNick(s){
404 - let h = 0;
405 - for (let i = 0; i < s.length; i++) { h = ((h << 5) - h) + s.charCodeAt(i); h |= 0; }
406 - return (h >>> 0);
407 - }
408 - function colorFor(nick){
409 - const idx = hashNick(nick || 'anon') % PALETTE.length;
410 - return PALETTE[idx];
411 - }
412 - function renderRoster(users){
413 - const count = (users ? users.length : 0);
414 - if (usersCount) usersCount.textContent = String(count);
415 - }
416 - function append(msg){
417 - const div = document.createElement('div');
418 - div.className = 'line';
419 - const ts = new Date(msg.ts).toLocaleTimeString([], { hour12: false, hour: '2-digit', minute: '2-digit', second: '2-digit' });
420 - const nick = (msg.user || 'anon');
421 - const color = colorFor(nick);
422 - if (msg.event === 'roster') { renderRoster(msg.users || []); return; }
423 - if (msg.event === 'rename') {
424 - div.className = 'line event';
425 - div.innerHTML = '<span class="ts">[' + ts + ']</span> ' + escapeHTML(msg.user || 'anon') + ' -> ' + escapeHTML(msg.text || '') + ' changed';
426 - } else if (msg.event === 'joined' || msg.event === 'left') {
427 - const verb = msg.event === 'joined' ? 'joined' : 'left';
428 - div.className = 'line event';
429 - div.innerHTML = '<span class="ts">[' + ts + ']</span> ' + escapeHTML(nick) + ' ' + verb;
430 - } else {
431 - div.innerHTML = '<span class="ts">[' + ts + ']</span> <span class="usr" style="color:' + color + '">' +
432 - nick + '</span>: ' + escapeHTML(msg.text || '');
433 - }
434 - log.appendChild(div);
435 - log.scrollTop = log.scrollHeight;
436 - }
437 - function escapeHTML(s){
438 - return s.replace(/[&<>\"]/g, c => ({'&':'&amp;','<':'&lt;','>':'&gt;','\"':'&quot;'}[c]));
439 - }
440 -
441 - const wsProto = location.protocol === 'https:' ? 'wss' : 'ws';
442 - const basePath = location.pathname.endsWith('/') ? location.pathname : (location.pathname + '/');
443 - const ws = new WebSocket(wsProto + '://' + location.host + basePath + 'ws');
444 - ws.onmessage = (e) => { try{ append(JSON.parse(e.data)); }catch(_){ } };
445 - ws.onopen = () => {
446 - try{ ws.send(JSON.stringify({ user: (user.value || 'anon'), text: '', uid: clientUID })); }catch(_){ }
447 - };
448 - function send(){
449 - const payload = { user: (user.value || 'anon'), text: cmd.value.trim(), uid: clientUID };
450 - if(!payload.text) return;
451 - ws.send(JSON.stringify(payload));
452 - cmd.value='';
453 - }
454 - // Handle IME composition properly to avoid duplicated last character
455 - // on Enter when using Korean/Japanese/Chinese input methods.
456 - cmd.addEventListener('keydown', e => {
457 - if (e.isComposing || e.keyCode === 229) { return; }
458 - if (e.key === 'Enter') {
459 - e.preventDefault();
460 - e.stopPropagation();
461 - send();
462 - // Ensure focus stays on the message input on mobile
463 - setTimeout(() => cmd.focus(), 0);
464 - }
465 - });
466 - // Focus command line on load
467 - setTimeout(()=>cmd.focus(), 0);
468 - </script>
469 -</body>
470 -</html>`))
sdk/go/examples/http-client/main.go deleted
-103
@@ -1,103 +0,0 @@
1 -package main
2 -
3 -import (
4 - "context"
5 - "fmt"
6 - "net"
7 - "net/http"
8 - "os"
9 - "os/signal"
10 - "syscall"
11 - "time"
12 -
13 - "github.com/rs/zerolog/log"
14 - "github.com/spf13/cobra"
15 -
16 - sdk "github.com/gosuda/relaydns/sdk/go"
17 -)
18 -
19 -var rootCmd = &cobra.Command{
20 - Use: "relaydns-client",
21 - Short: "RelayDNS demo client (local HTTP backend + libp2p advertiser)",
22 - RunE: runClient,
23 -}
24 -
25 -var (
26 - flagServerURL string
27 - flagPort int
28 - flagName string
29 -)
30 -
31 -func init() {
32 - flags := rootCmd.PersistentFlags()
33 - flags.StringVar(&flagServerURL, "server-url", "http://relaydns.gosuda.org", "relayserver admin base URL to auto-fetch multiaddrs from /health")
34 - flags.IntVar(&flagPort, "port", 8081, "local backend HTTP port")
35 - flags.StringVar(&flagName, "name", "example-backend", "backend display name shown on server UI")
36 -}
37 -
38 -func main() {
39 - if err := rootCmd.Execute(); err != nil {
40 - log.Fatal().Err(err).Msg("execute root command")
41 - }
42 -}
43 -
44 -func runClient(cmd *cobra.Command, args []string) error {
45 - ctx, cancel := context.WithCancel(context.Background())
46 - defer cancel() // Ensure context is cancelled on all exit paths
47 -
48 - // 1) start local HTTP backend
49 - var relayClient *sdk.RelayClient
50 - httpLn, err := net.Listen("tcp", fmt.Sprintf(":%d", flagPort))
51 - if err != nil {
52 - log.Fatal().Err(err).Msg("failed to listen")
53 - }
54 - log.Info().Msgf("[client] local backend http listening on %s", httpLn.Addr().String())
55 - handler := NewHandler(httpLn.Addr().String(), flagName, func() string {
56 - if relayClient == nil {
57 - return "Starting..."
58 - }
59 - return relayClient.ServerStatus()
60 - })
61 - httpSrv := &http.Server{Handler: handler, ReadHeaderTimeout: 5 * time.Second, IdleTimeout: 60 * time.Second}
62 - go func() {
63 - if err := httpSrv.Serve(httpLn); err != nil && err != http.ErrServerClosed {
64 - log.Error().Err(err).Msg(" http backend error")
65 - }
66 - }()
67 -
68 - // 2) libp2p client
69 - client, err := sdk.NewClient(ctx, sdk.ClientConfig{
70 - Name: flagName,
71 - TargetTCP: fmt.Sprintf("127.0.0.1:%d", flagPort),
72 - ServerURL: flagServerURL,
73 - })
74 - if err != nil {
75 - return fmt.Errorf("new client: %w", err)
76 - }
77 - if err := client.Start(ctx); err != nil {
78 - return fmt.Errorf("start client: %w", err)
79 - }
80 - relayClient = client
81 -
82 - // wait for termination
83 - sig := make(chan os.Signal, 1)
84 - signal.Notify(sig, syscall.SIGINT, syscall.SIGTERM)
85 - <-sig
86 - log.Info().Msg("[client] shutting down...")
87 -
88 - // Shutdown sequence:
89 - // 1. Close client (waits for goroutines, closes libp2p host)
90 - if err := client.Close(); err != nil {
91 - log.Warn().Err(err).Msg("[client] client close error")
92 - }
93 -
94 - // 2. Shutdown HTTP server with a fresh context (with timeout)
95 - shutdownCtx, shutdownCancel := context.WithTimeout(context.Background(), 5*time.Second)
96 - defer shutdownCancel()
97 - if err := httpSrv.Shutdown(shutdownCtx); err != nil {
98 - log.Error().Err(err).Msg("[client] http server shutdown error")
99 - }
100 -
101 - log.Info().Msg("[client] shutdown complete")
102 - return nil
103 -}
sdk/go/examples/http-client/view.go deleted
-70
@@ -1,70 +0,0 @@
1 -package main
2 -
3 -import (
4 - "html/template"
5 - "net/http"
6 - "time"
7 -
8 - "github.com/go-chi/chi/v5"
9 -)
10 -
11 -// serveClientHTTP builds the local backend router using chi.
12 -// getStatus should return a short string like "Connected" or "Connecting...".
13 -func NewHandler(addr string, name string, getStatus func() string) http.Handler {
14 - r := chi.NewRouter()
15 - r.Get("/", func(w http.ResponseWriter, r *http.Request) {
16 - status := getStatus()
17 - statusClass := "disconnected"
18 - if status == "Connected" {
19 - statusClass = "connected"
20 - }
21 - data := struct {
22 - Now string
23 - Name string
24 - Addr string
25 - Status string
26 - StatusClass string
27 - }{
28 - Now: time.Now().Format(time.RFC1123),
29 - Name: name,
30 - Addr: addr,
31 - Status: status,
32 - StatusClass: statusClass,
33 - }
34 - _ = clientPage.Execute(w, data)
35 - })
36 - r.Get("/healthz", func(w http.ResponseWriter, r *http.Request) {
37 - w.WriteHeader(http.StatusOK)
38 - _, _ = w.Write([]byte("ok"))
39 - })
40 - return r
41 -}
42 -
43 -var clientPage = template.Must(template.New("index").Parse(`<!DOCTYPE html>
44 -<html lang="en">
45 -<head>
46 - <meta charset="UTF-8">
47 - <title>RelayDNS Backend</title>
48 - <style>
49 - body { font-family: sans-serif; background: #f9f9f9; padding: 40px; }
50 - h1 { color: #333; }
51 - footer { margin-top: 40px; color: #666; font-size: 0.9em; }
52 - .card { background: white; border-radius: 12px; padding: 24px; box-shadow: 0 2px 6px rgba(0,0,0,0.1); }
53 - .stat { display:inline-flex; align-items:center; gap:8px; padding:6px 10px; border-radius:999px; font-weight:700; font-size:14px }
54 - .stat.connected { background:#ecfdf5; color:#065f46 }
55 - .stat.disconnected { background:#fee2e2; color:#b91c1c }
56 - .stat .dot { width:8px; height:8px; border-radius:999px; background:#10b981; display:inline-block }
57 - .stat.disconnected .dot { background:#ef4444 }
58 - </style>
59 - </head>
60 -<body>
61 - <div class="card">
62 - <h1>🚀 RelayDNS Backend</h1>
63 - <p>This page is served from the backend node.</p>
64 - <p>Current time: <b>{{.Now}}</b></p>
65 - <p>Name: <b>{{.Name}}</b></p>
66 - <p>Server Status: <span class="stat {{.StatusClass}}"><span class="dot"></span>{{.Status}}</span></p>
67 - </div>
68 - <footer>relaydns demo client — served locally at {{.Addr}}</footer>
69 -</body>
70 -</html>`))
sdk/python/README.md deleted
-1
@@ -1 +0,0 @@
1 -# Python SDK
\ No newline at end of file
sdk/rust/README.md deleted
-1
@@ -1 +0,0 @@
1 -# Rust SDK
\ No newline at end of file
sdk/rust/a.rs
sdk/spec.md deleted
-1106
@@ -1,1106 +0,0 @@
1 -# RelayDNS SDK Development Specification
2 -
3 -> **Version**: 1.0.0
4 -> **Last Updated**: 2025-10-23
5 -> **Target Languages**: Go, TypeScript, Python, Rust
6 -
7 ----
8 -
9 -## 📋 Table of Contents
10 -
11 -1. [Overview](#overview)
12 -2. [Core Concepts](#core-concepts)
13 -3. [Architecture](#architecture)
14 -4. [API Specification](#api-specification)
15 -5. [Implementation Guide](#implementation-guide)
16 -6. [Language-Specific Guides](#language-specific-guides)
17 -7. [Testing](#testing)
18 -8. [Example Code](#example-code)
19 -
20 ----
21 -
22 -## Overview
23 -
24 -### What is RelayDNS?
25 -
26 -RelayDNS is a **libp2p-based lightweight P2P proxy layer**. It makes local services (SSH, HTTP, WebSocket, etc.) behind NAT externally accessible and provides DNS-style simple service discovery.
27 -
28 -### Why Do We Need an SDK?
29 -
30 -By **embedding** a RelayDNS client in your application:
31 -- Automatically advertise local services to the P2P network
32 -- Enable external access even behind NAT/firewalls
33 -- Operate without centralized reverse proxies
34 -
35 -### The Role of the SDK
36 -
37 -```
38 -┌─────────────┐
39 -│ Your App │
40 -├─────────────┤
41 -│ SDK Client │ ← This is what we'll implement
42 -├─────────────┤
43 -│ libp2p │
44 -└─────────────┘
45 - ↕ P2P
46 -┌─────────────┐
47 -│ RelayDNS │
48 -│ Server │
49 -└─────────────┘
50 -```
51 -
52 ----
53 -
54 -## Core Concepts
55 -
56 -### 1. libp2p
57 -
58 -**A peer-to-peer networking framework**
59 -- Each node has a unique **Peer ID**
60 -- Supports multiple **Transports** (TCP, QUIC, WebSocket)
61 -- NAT traversal capabilities (Relay, Hole Punching)
62 -
63 -### 2. GossipSub
64 -
65 -**A Pub/Sub messaging protocol**
66 -- Subscribe to topics to receive messages
67 -- Broadcast peer advertisements
68 -- Provides distributed service discovery
69 -
70 -### 3. Stream Handler
71 -
72 -**Proxies libp2p streams to local TCP**
73 -- Automatically forwards connections from other peers to local services
74 -- Bidirectional byte copying
75 -- Error handling and cleanup
76 -
77 -### 4. Bootstrap Peers
78 -
79 -**Network entry points**
80 -- Known peers for initial connection
81 -- Dynamically fetched from the server's `/health` endpoint
82 -
83 ----
84 -
85 -## Architecture
86 -
87 -### Overall Structure
88 -
89 -```
90 -┌──────────────────────────────────────────────────────────┐
91 -│ Your Application │
92 -│ (HTTP Server, SSH Daemon, WebSocket Service, etc.) │
93 -└───────────────────────────┬──────────────────────────────┘
94 - │ TCP (127.0.0.1:8081)
95 -┌───────────────────────────▼──────────────────────────────┐
96 -│ SDK Client │
97 -│ ┌────────────────────────────────────────────────────┐ │
98 -│ │ Health Client : Fetch bootstrap peers │ │
99 -│ ├────────────────────────────────────────────────────┤ │
100 -│ │ libp2p Node : P2P networking (TCP/QUIC/WS) │ │
101 -│ ├────────────────────────────────────────────────────┤ │
102 -│ │ GossipSub : Peer discovery (Pub/Sub) │ │
103 -│ ├────────────────────────────────────────────────────┤ │
104 -│ │ Stream Handler : Stream → TCP proxy │ │
105 -│ ├────────────────────────────────────────────────────┤ │
106 -│ │ Advertisement : Advertise service every 30s │ │
107 -│ └────────────────────────────────────────────────────┘ │
108 -└───────────────────────────┬──────────────────────────────┘
109 - │ libp2p streams
110 -┌───────────────────────────▼──────────────────────────────┐
111 -│ RelayDNS Server │
112 -│ • Bootstrap coordinator │
113 -│ • GossipSub topic relay │
114 -│ • Admin UI (peer list) │
115 -│ • HTTP/WS proxy endpoints │
116 -└──────────────────────────────────────────────────────────┘
117 -```
118 -
119 -### Data Flow
120 -
121 -#### 1. Startup Sequence
122 -```
123 -1. [SDK] GET /health → [Server]
124 - ← Returns bootstrap peer addresses
125 -
126 -2. [SDK] Create libp2p node
127 - • Generate Ed25519 key
128 - • Enable TCP/QUIC transports
129 - • Configure Noise security
130 -
131 -3. [SDK] Connect to bootstrap peers
132 - • Dial each peer
133 - • Join the network
134 -
135 -4. [SDK] Join GossipSub topic
136 - • Subscribe to "/relaydns/peers/1.0.0"
137 - • Start receiving advertisements
138 -
139 -5. [SDK] Register stream handler
140 - • "/relaydns/1.0.0" protocol
141 - • Wait for inbound connections
142 -
143 -6. [SDK] Publish own advertisement
144 - • Broadcast peer information
145 - • Repeat every 30 seconds
146 -```
147 -
148 -#### 2. Connection Flow
149 -```
150 -[User] → [Server] → [SDK] → [Your App]
151 -
152 -1. User selects peer in server UI
153 -2. Server opens libp2p stream
154 -3. SDK receives stream
155 -4. SDK opens local TCP connection (127.0.0.1:8081)
156 -5. Start bidirectional byte copying
157 -```
158 -
159 ----
160 -
161 -## API Specification
162 -
163 -### Configuration
164 -
165 -All SDKs must provide the same configuration interface.
166 -
167 -#### Required Fields (3)
168 -
169 -| Field | Type | Description | Example |
170 -|-------|------|-------------|---------|
171 -| `ServerURL` | string | RelayDNS server base URL | `"http://localhost:8080"` |
172 -| `TargetTCP` | string | Local service address | `"127.0.0.1:8081"` |
173 -| `Name` | string | Display name for UI | `"my-http-service"` |
174 -
175 -#### Optional Fields (3)
176 -
177 -| Field | Type | Default | Description |
178 -|-------|------|---------|-------------|
179 -| `Protocol` | string | `"/relaydns/1.0.0"` | libp2p protocol string |
180 -| `Topic` | string | `"/relaydns/peers/1.0.0"` | GossipSub topic |
181 -| `Bootstrap` | []string | `[]` (fetched from server) | Custom bootstrap peers |
182 -
183 -#### Validation Rules
184 -
185 -- `ServerURL`: Must include `http://` or `https://`
186 -- `TargetTCP`: Must be in `host:port` format
187 -- `Name`: Non-empty string
188 -- `Bootstrap`: Valid multiaddr format (e.g., `/ip4/1.2.3.4/tcp/4001/p2p/QmXxX...`)
189 -
190 -### Client Interface
191 -
192 -#### Methods
193 -
194 -```
195 -NewClient(config: ClientConfig) -> (Client, Error)
196 -```
197 -- Create a new client instance
198 -- Validate configuration
199 -- Initialize libp2p host
200 -- Configure GossipSub
201 -- **Does not start yet** (requires Start call)
202 -
203 -```
204 -Start() -> Error
205 -```
206 -- Connect to bootstrap peers
207 -- Join GossipSub topic
208 -- Register stream handler
209 -- Start advertising
210 -- Runs in background without blocking
211 -
212 -```
213 -Close() -> Error
214 -```
215 -- Close all connections
216 -- Unsubscribe from GossipSub
217 -- Clean up resources
218 -- Graceful shutdown
219 -
220 -```
221 -PeerID() -> string
222 -```
223 -- Returns the client's libp2p Peer ID
224 -- Read-only
225 -- For debugging/logging
226 -
227 -### Health Endpoint
228 -
229 -#### Request
230 -```http
231 -GET {ServerURL}/health
232 -```
233 -
234 -#### Response
235 -```json
236 -{
237 - "status": "healthy",
238 - "peers": [
239 - "/ip4/1.2.3.4/tcp/4001/p2p/QmServerPeerID",
240 - "/ip4/5.6.7.8/tcp/4001/p2p/QmOtherPeerID"
241 - ],
242 - "version": "1.0.0"
243 -}
244 -```
245 -
246 -#### Error Handling
247 -- Server unreachable: Clear error message
248 -- JSON parsing failure: Configuration validation failure
249 -- Empty peers array: Warning log, continue (can use fallback bootstrap)
250 -
251 -### Advertisement Message
252 -
253 -#### Format (JSON)
254 -```json
255 -{
256 - "peer_id": "QmXxXxXxXxXxXxXxXxXxXxXxXxXxX",
257 - "name": "my-http-service",
258 - "protocol": "/relaydns/1.0.0",
259 - "timestamp": 1729728000
260 -}
261 -```
262 -
263 -#### Publishing Cycle
264 -- Initial: Immediately after Start()
265 -- Thereafter: Every 30 seconds
266 -- On shutdown: Stop advertising (automatic)
267 -
268 ----
269 -
270 -## Implementation Guide
271 -
272 -### Step-by-Step Implementation
273 -
274 -#### Step 1: Health Endpoint Client
275 -
276 -**Goal**: Fetch bootstrap peer information from server
277 -
278 -**Implementation**:
279 -```
280 -function fetchHealth(serverURL):
281 - url = serverURL + "/health"
282 - response = HTTP_GET(url)
283 - if response.status != 200:
284 - throw Error("Health check failed")
285 -
286 - data = JSON_PARSE(response.body)
287 - return data.peers
288 -```
289 -
290 -**Testing**:
291 -```bash
292 -curl http://localhost:8080/health
293 -# Response should contain "peers" array
294 -```
295 -
296 -#### Step 2: libp2p Node Initialization
297 -
298 -**Goal**: Set up P2P networking foundation
299 -
300 -**Required Components**:
301 -1. **Identity**: Generate Ed25519 keypair
302 -2. **Transports**: Enable TCP, QUIC
303 -3. **Security**: Noise protocol
304 -4. **Multiplexing**: Yamux
305 -5. **NAT**: Enable AutoNAT, Relay, Hole Punching
306 -
307 -**Pseudocode**:
308 -```
309 -function createLibp2pHost():
310 - privateKey = generateEd25519Key()
311 -
312 - host = newLibp2pHost({
313 - identity: privateKey,
314 - transports: [TCP, QUIC],
315 - security: Noise,
316 - muxer: Yamux,
317 - enableNAT: true,
318 - enableRelay: true,
319 - enableHolePunching: true
320 - })
321 -
322 - return host
323 -```
324 -
325 -#### Step 3: GossipSub Configuration
326 -
327 -**Goal**: Enable Pub/Sub messaging
328 -
329 -**Implementation**:
330 -```
331 -function setupGossipSub(host):
332 - pubsub = newGossipSub(host)
333 - topic = pubsub.join("/relaydns/peers/1.0.0")
334 - subscription = topic.subscribe()
335 -
336 - return (pubsub, topic, subscription)
337 -```
338 -
339 -**Message Receiving**:
340 -```
341 -function handleMessages(subscription):
342 - while message = subscription.next():
343 - data = JSON_PARSE(message.data)
344 - log("Received peer: " + data.name + " (" + data.peer_id + ")")
345 -```
346 -
347 -#### Step 4: Bootstrap Connection
348 -
349 -**Goal**: Join the network
350 -
351 -**Implementation**:
352 -```
353 -function connectBootstrap(host, bootstrapAddrs):
354 - for addr in bootstrapAddrs:
355 - try:
356 - multiaddr = parseMultiaddr(addr)
357 - peerInfo = extractPeerInfo(multiaddr)
358 - host.connect(peerInfo)
359 - log("Connected to bootstrap: " + peerInfo.id)
360 - catch error:
361 - log("Failed to connect: " + addr)
362 - continue // Try next peer
363 -```
364 -
365 -**Note**: Don't terminate the program if all bootstrap connections fail, just log warnings
366 -
367 -#### Step 5: Stream Handler
368 -
369 -**Goal**: Proxy inbound connections to local service
370 -
371 -**Implementation**:
372 -```
373 -function registerStreamHandler(host, protocol, targetTCP):
374 - host.setStreamHandler(protocol, function(stream):
375 - handleStream(stream, targetTCP)
376 - )
377 -
378 -function handleStream(stream, targetTCP):
379 - try:
380 - // Connect to local service
381 - tcpConn = connectTCP(targetTCP, timeout=5s)
382 -
383 - // Bidirectional copy
384 - go copyAsync(stream -> tcpConn)
385 - go copyAsync(tcpConn -> stream)
386 -
387 - // Clean up when either side closes
388 - waitForEither()
389 -
390 - finally:
391 - stream.close()
392 - tcpConn.close()
393 -```
394 -
395 -**Error Handling**:
396 -- Local service down: Close stream immediately, log error
397 -- Copy error: Clean up both connections
398 -- Timeout: Give up after 5 seconds
399 -
400 -#### Step 6: Advertisement Loop
401 -
402 -**Goal**: Periodically advertise service
403 -
404 -**Implementation**:
405 -```
406 -function startAdvertisement(pubsub, topic, peerID, name, protocol):
407 - // Advertise immediately
408 - publishAdvertisement(topic, peerID, name, protocol)
409 -
410 - // Repeat every 30 seconds
411 - ticker = newTicker(30 seconds)
412 - while true:
413 - wait(ticker.tick)
414 - publishAdvertisement(topic, peerID, name, protocol)
415 -
416 -function publishAdvertisement(topic, peerID, name, protocol):
417 - message = {
418 - "peer_id": peerID,
419 - "name": name,
420 - "protocol": protocol,
421 - "timestamp": currentUnixTime()
422 - }
423 -
424 - data = JSON_STRINGIFY(message)
425 - topic.publish(data)
426 -```
427 -
428 -### Error Handling Strategy
429 -
430 -#### 1. Startup Errors
431 -
432 -| Error | Cause | Handling |
433 -|-------|-------|----------|
434 -| Health endpoint failure | Server down or network issue | Fail fast, clear error |
435 -| Bootstrap connection failure | Bad address or firewall | Warning log, continue |
436 -| GossipSub subscription failure | libp2p configuration issue | Fail fast, return error |
437 -
438 -#### 2. Runtime Errors
439 -
440 -| Error | Cause | Handling |
441 -|-------|-------|----------|
442 -| Local service down | Target TCP connection failure | Close stream, log error |
443 -| Peer disconnection | Network instability | Retry with backoff |
444 -| Stream error | Protocol mismatch | Clean up stream, log error |
445 -
446 -#### 3. Reconnection Logic
447 -
448 -```
449 -function reconnectWithBackoff():
450 - delay = 1 second
451 - maxDelay = 60 seconds
452 -
453 - while true:
454 - try:
455 - fetchHealth()
456 - connectBootstrap()
457 - rejoinGossipSub()
458 - return SUCCESS
459 - catch error:
460 - log("Reconnect failed, retry in " + delay)
461 - sleep(delay)
462 - delay = min(delay * 2, maxDelay)
463 -```
464 -
465 ----
466 -
467 -## Language-Specific Guides
468 -
469 -### Go
470 -
471 -#### Dependencies
472 -```go
473 -require (
474 - github.com/libp2p/go-libp2p v0.32.0
475 - github.com/libp2p/go-libp2p-pubsub v0.10.0
476 - github.com/multiformats/go-multiaddr v0.12.0
477 -)
478 -```
479 -
480 -#### Core Types
481 -```go
482 -type ClientConfig struct {
483 - ServerURL string
484 - TargetTCP string
485 - Name string
486 - Protocol string
487 - Topic string
488 - Bootstrap []string
489 -}
490 -
491 -type Client struct {
492 - config ClientConfig
493 - host host.Host
494 - ps *pubsub.PubSub
495 - topic *pubsub.Topic
496 - sub *pubsub.Subscription
497 -}
498 -```
499 -
500 -#### Patterns
501 -- Use Context: `ctx context.Context`
502 -- Cleanup: `defer client.Close()`
503 -- Concurrency: goroutines + channels
504 -
505 -#### Example
506 -```go
507 -ctx := context.Background()
508 -client, err := sdk.NewClient(ctx, sdk.ClientConfig{
509 - ServerURL: "http://localhost:8080",
510 - TargetTCP: "127.0.0.1:8081",
511 - Name: "demo",
512 -})
513 -if err != nil {
514 - log.Fatal(err)
515 -}
516 -defer client.Close()
517 -
518 -if err := client.Start(ctx); err != nil {
519 - log.Fatal(err)
520 -}
521 -
522 -select {} // Keep running
523 -```
524 -
525 -### TypeScript
526 -
527 -#### Dependencies
528 -```json
529 -{
530 - "dependencies": {
531 - "libp2p": "^1.0.0",
532 - "@chainsafe/libp2p-gossipsub": "^12.0.0",
533 - "@libp2p/tcp": "^9.0.0",
534 - "@libp2p/noise": "^14.0.0"
535 - }
536 -}
537 -```
538 -
539 -#### Core Types
540 -```typescript
541 -interface ClientConfig {
542 - serverURL: string;
543 - targetTCP: string;
544 - name: string;
545 - protocol?: string;
546 - topic?: string;
547 - bootstrap?: string[];
548 -}
549 -
550 -class Client {
551 - constructor(config: ClientConfig);
552 - async start(): Promise<void>;
553 - async close(): Promise<void>;
554 - getPeerID(): string;
555 -}
556 -```
557 -
558 -#### Patterns
559 -- All I/O uses `async/await`
560 -- Cleanup: `try/finally` or `using`
561 -- Browser: WebRTC only (requires signaling)
562 -
563 -#### Example
564 -```typescript
565 -const client = new Client({
566 - serverURL: 'http://localhost:8080',
567 - targetTCP: '127.0.0.1:8081',
568 - name: 'demo'
569 -});
570 -
571 -await client.start();
572 -console.log(`Peer ID: ${client.getPeerID()}`);
573 -
574 -process.on('SIGINT', async () => {
575 - await client.close();
576 - process.exit(0);
577 -});
578 -```
579 -
580 -### Python
581 -
582 -#### Dependencies
583 -```toml
584 -[project]
585 -dependencies = [
586 - "libp2p>=0.1.0",
587 - "aiohttp>=3.9.0",
588 -]
589 -```
590 -
591 -#### Core Types
592 -```python
593 -@dataclass
594 -class ClientConfig:
595 - server_url: str
596 - target_tcp: str
597 - name: str
598 - protocol: str = "/relaydns/1.0.0"
599 - topic: str = "/relaydns/peers/1.0.0"
600 - bootstrap: List[str] = field(default_factory=list)
601 -
602 -class Client:
603 - def __init__(self, config: ClientConfig): ...
604 - async def start(self) -> None: ...
605 - async def close(self) -> None: ...
606 - def peer_id(self) -> str: ...
607 -```
608 -
609 -#### Patterns
610 -- `async/await` (asyncio or trio)
611 -- Context manager: `async with Client(...)`
612 -- Use type hints
613 -
614 -#### Example
615 -```python
616 -async def main():
617 - config = ClientConfig(
618 - server_url="http://localhost:8080",
619 - target_tcp="127.0.0.1:8081",
620 - name="demo"
621 - )
622 -
623 - async with Client(config) as client:
624 - await client.start()
625 - print(f"Peer ID: {client.peer_id()}")
626 - await asyncio.Event().wait()
627 -
628 -asyncio.run(main())
629 -```
630 -
631 -### Rust
632 -
633 -#### Dependencies
634 -```toml
635 -[dependencies]
636 -libp2p = { version = "0.53", features = ["tcp", "quic", "noise", "yamux", "gossipsub"] }
637 -tokio = { version = "1.0", features = ["full"] }
638 -reqwest = { version = "0.11", features = ["json"] }
639 -```
640 -
641 -#### Core Types
642 -```rust
643 -pub struct ClientConfig {
644 - pub server_url: String,
645 - pub target_tcp: String,
646 - pub name: String,
647 - pub protocol: Option<String>,
648 - pub topic: Option<String>,
649 - pub bootstrap: Option<Vec<String>>,
650 -}
651 -
652 -pub struct Client {
653 - config: ClientConfig,
654 - swarm: Swarm<Behaviour>,
655 -}
656 -
657 -impl Client {
658 - pub async fn new(config: ClientConfig) -> Result<Self, Error>;
659 - pub async fn start(&mut self) -> Result<(), Error>;
660 - pub async fn close(self) -> Result<(), Error>;
661 - pub fn peer_id(&self) -> PeerId;
662 -}
663 -```
664 -
665 -#### Patterns
666 -- Swarm-based architecture
667 -- `Result<T, E>` error handling
668 -- Builder pattern (optional)
669 -
670 -#### Example
671 -```rust
672 -#[tokio::main]
673 -async fn main() -> Result<(), Box<dyn std::error::Error>> {
674 - let config = ClientConfig {
675 - server_url: "http://localhost:8080".to_string(),
676 - target_tcp: "127.0.0.1:8081".to_string(),
677 - name: "demo".to_string(),
678 - ..Default::default()
679 - };
680 -
681 - let mut client = Client::new(config).await?;
682 - client.start().await?;
683 -
684 - println!("Peer ID: {}", client.peer_id());
685 -
686 - tokio::signal::ctrl_c().await?;
687 - client.close().await?;
688 -
689 - Ok(())
690 -}
691 -```
692 -
693 ----
694 -
695 -## Testing
696 -
697 -### Test Environment Setup
698 -
699 -#### 1. Start RelayDNS Server
700 -```bash
701 -# Using Docker Compose
702 -docker compose up -d
703 -
704 -# Verify server
705 -curl http://localhost:8080/health
706 -```
707 -
708 -#### 2. Start Local Service
709 -```bash
710 -# Simple HTTP server
711 -python -m http.server 8081
712 -
713 -# Or
714 -echo "Hello RelayDNS" > index.html
715 -python -m http.server 8081
716 -```
717 -
718 -### Unit Tests
719 -
720 -#### Config Validation
721 -```
722 -TEST: Error on missing required field
723 - config = ClientConfig{Name: "test"}
724 - client = NewClient(config)
725 - EXPECT: error "ServerURL is required"
726 -
727 -TEST: Success with valid config
728 - config = ClientConfig{
729 - ServerURL: "http://localhost:8080",
730 - TargetTCP: "127.0.0.1:8081",
731 - Name: "test"
732 - }
733 - client = NewClient(config)
734 - EXPECT: no error
735 -```
736 -
737 -#### Health Endpoint
738 -```
739 -TEST: Parse valid response
740 - response = '{"status":"healthy","peers":["addr1"],"version":"1.0"}'
741 - peers = parseHealth(response)
742 - EXPECT: peers = ["addr1"]
743 -
744 -TEST: Error when server unavailable
745 - serverURL = "http://nonexistent:9999"
746 - EXPECT: error "connection refused"
747 -```
748 -
749 -### Integration Tests
750 -
751 -#### 1. Basic Connection Test
752 -```
753 -GIVEN: RelayDNS server is running
754 - AND: Local HTTP server is running on port 8081
755 -
756 -WHEN: SDK client starts
757 - config = ClientConfig{
758 - ServerURL: "http://localhost:8080",
759 - TargetTCP: "127.0.0.1:8081",
760 - Name: "test-client"
761 - }
762 - client.Start()
763 -
764 -THEN:
765 - - Health endpoint call succeeds
766 - - Bootstrap peers connected successfully
767 - - GossipSub topic joined successfully
768 - - "test-client" appears in server Admin UI
769 -```
770 -
771 -#### 2. Proxy Test
772 -```
773 -GIVEN: Client is started
774 - AND: Local server responds with "Hello"
775 -
776 -WHEN: Click peer in server UI → Click "Open"
777 -
778 -THEN:
779 - - Page opens in new tab
780 - - "Hello" text is displayed
781 - - Stream is proxied to local port 8081
782 -```
783 -
784 -#### 3. Reconnection Test
785 -```
786 -GIVEN: Client is running
787 -
788 -WHEN: Server restarts
789 - docker compose restart
790 -
791 -THEN:
792 - - Client attempts to reconnect
793 - - Backoff logs are printed
794 - - Reconnection succeeds after server restart
795 - - Reappears in UI
796 -```
797 -
798 -#### 4. Error Handling Test
799 -```
800 -TEST: When local service is down
801 -GIVEN: Client is running
802 -WHEN: Local server is stopped (kill python)
803 - AND: Connection attempt from server
804 -THEN:
805 - - Stream closes immediately
806 - - Error log: "connection refused"
807 - - Client continues running
808 -```
809 -
810 -### Test Checklist
811 -
812 -Verify the following in a real environment:
813 -
814 -- [ ] Health endpoint call succeeds
815 -- [ ] Connected to bootstrap peers
816 -- [ ] Joined GossipSub topic
817 -- [ ] Published own advertisement
818 -- [ ] Received other peer advertisements
819 -- [ ] Displayed in server Admin UI
820 -- [ ] Proxy connection works
821 -- [ ] Handles local service down gracefully
822 -- [ ] Graceful shutdown with Ctrl+C
823 -- [ ] Normal operation after restart
824 -
825 ----
826 -
827 -## Example Code
828 -
829 -### Minimal Example (Go)
830 -
831 -```go
832 -package main
833 -
834 -import (
835 - "context"
836 - "log"
837 -
838 - sdk "github.com/your-org/relaydns-sdk-go"
839 -)
840 -
841 -func main() {
842 - ctx := context.Background()
843 -
844 - // Create client
845 - client, err := sdk.NewClient(ctx, sdk.ClientConfig{
846 - ServerURL: "http://localhost:8080",
847 - TargetTCP: "127.0.0.1:8081",
848 - Name: "my-service",
849 - })
850 - if err != nil {
851 - log.Fatalf("Failed to create client: %v", err)
852 - }
853 - defer client.Close()
854 -
855 - // Start
856 - if err := client.Start(ctx); err != nil {
857 - log.Fatalf("Failed to start client: %v", err)
858 - }
859 -
860 - log.Printf("✓ Started. Peer ID: %s", client.PeerID())
861 -
862 - // Keep running
863 - select {}
864 -}
865 -```
866 -
867 -### Custom Bootstrap (TypeScript)
868 -
869 -```typescript
870 -import { Client, ClientConfig } from 'relaydns-sdk';
871 -
872 -const config: ClientConfig = {
873 - serverURL: 'http://localhost:8080',
874 - targetTCP: '127.0.0.1:8081',
875 - name: 'custom-service',
876 - bootstrap: [
877 - '/ip4/1.2.3.4/tcp/4001/p2p/QmPeerID1',
878 - '/ip4/5.6.7.8/tcp/4001/p2p/QmPeerID2'
879 - ]
880 -};
881 -
882 -const client = new Client(config);
883 -
884 -try {
885 - await client.start();
886 - console.log(`✓ Started. Peer ID: ${client.getPeerID()}`);
887 -
888 - await new Promise(() => {}); // Keep running
889 -} catch (error) {
890 - console.error('Failed:', error);
891 - process.exit(1);
892 -}
893 -```
894 -
895 -### Error Handling (Python)
896 -
897 -```python
898 -import asyncio
899 -import logging
900 -from relaydns_sdk import Client, ClientConfig
901 -
902 -logging.basicConfig(level=logging.INFO)
903 -logger = logging.getLogger(__name__)
904 -
905 -async def main():
906 - config = ClientConfig(
907 - server_url="http://localhost:8080",
908 - target_tcp="127.0.0.1:8081",
909 - name="python-service"
910 - )
911 -
912 - client = Client(config)
913 -
914 - try:
915 - await client.start()
916 - logger.info(f"✓ Started. Peer ID: {client.peer_id()}")
917 -
918 - # Keep running
919 - await asyncio.Event().wait()
920 -
921 - except ConnectionError as e:
922 - logger.error(f"✗ Connection failed: {e}")
923 - return 1
924 -
925 - except Exception as e:
926 - logger.error(f"✗ Unexpected error: {e}")
927 - return 1
928 -
929 - finally:
930 - await client.close()
931 - logger.info("✓ Closed gracefully")
932 -
933 - return 0
934 -
935 -if __name__ == "__main__":
936 - exit_code = asyncio.run(main())
937 - exit(exit_code)
938 -```
939 -
940 -### Production Example (Rust)
941 -
942 -```rust
943 -use relaydns_sdk::{Client, ClientConfig};
944 -use tokio;
945 -use tracing::{info, error};
946 -
947 -#[tokio::main]
948 -async fn main() -> Result<(), Box<dyn std::error::Error>> {
949 - // Initialize logging
950 - tracing_subscriber::fmt::init();
951 -
952 - // Configuration
953 - let config = ClientConfig {
954 - server_url: "http://localhost:8080".to_string(),
955 - target_tcp: "127.0.0.1:8081".to_string(),
956 - name: "rust-service".to_string(),
957 - ..Default::default()
958 - };
959 -
960 - // Create client
961 - let mut client = Client::new(config).await.map_err(|e| {
962 - error!("Failed to create client: {}", e);
963 - e
964 - })?;
965 -
966 - // Start
967 - client.start().await.map_err(|e| {
968 - error!("Failed to start client: {}", e);
969 - e
970 - })?;
971 -
972 - info!("✓ Started. Peer ID: {}", client.peer_id());
973 -
974 - // Wait for shutdown signal
975 - tokio::select! {
976 - _ = tokio::signal::ctrl_c() => {
977 - info!("Received Ctrl+C, shutting down...");
978 - }
979 - }
980 -
981 - // Graceful shutdown
982 - client.close().await?;
983 - info!("✓ Closed gracefully");
984 -
985 - Ok(())
986 -}
987 -```
988 -
989 ----
990 -
991 -## Appendix
992 -
993 -### A. Multiaddr Format
994 -
995 -Address format used in RelayDNS:
996 -
997 -```
998 -/ip4/1.2.3.4/tcp/4001/p2p/QmPeerID...
999 -│ │ │ │ │ └─ Peer ID (required)
1000 -│ │ │ │ └───── Transport protocol
1001 -│ │ │ └────────── Port
1002 -│ │ └────────────── Transport
1003 -│ └────────────────────── IP address
1004 -└─────────────────────────── IP version
1005 -```
1006 -
1007 -Other examples:
1008 -- `/ip4/127.0.0.1/tcp/4001/p2p/Qm...` - Local TCP
1009 -- `/ip6/::1/tcp/4001/p2p/Qm...` - IPv6
1010 -- `/ip4/1.2.3.4/udp/4001/quic-v1/p2p/Qm...` - QUIC
1011 -
1012 -### B. Debugging Tips
1013 -
1014 -#### "Cannot connect to bootstrap"
1015 -```bash
1016 -# Check server status
1017 -curl http://localhost:8080/health
1018 -
1019 -# Check port
1020 -nc -zv localhost 4001
1021 -
1022 -# Check firewall
1023 -sudo ufw status
1024 -```
1025 -
1026 -#### "Stream handler not called"
1027 -```bash
1028 -# Verify protocol match
1029 -# Client: "/relaydns/1.0.0"
1030 -# Server: Same protocol
1031 -
1032 -# Check GossipSub messages in logs
1033 -# Should see "Published advertisement" messages
1034 -```
1035 -
1036 -#### "Local service connection refused"
1037 -```bash
1038 -# Check local service
1039 -nc -zv 127.0.0.1 8081
1040 -
1041 -# Or
1042 -curl http://127.0.0.1:8081
1043 -```
1044 -
1045 -### C. Performance Considerations
1046 -
1047 -#### Buffer Size
1048 -```
1049 -Recommended: 32KB read/write buffer
1050 -- Larger: Throughput ↑, Memory ↑
1051 -- Smaller: Latency ↓, Memory ↓
1052 -```
1053 -
1054 -#### GossipSub Tuning
1055 -```
1056 -Low latency:
1057 -- heartbeat: 500ms
1058 -- fanout: 8
1059 -
1060 -Bandwidth saving:
1061 -- heartbeat: 2s
1062 -- fanout: 4
1063 -```
1064 -
1065 -#### Connection Pooling
1066 -```
1067 -Problem: New TCP connection per stream
1068 -Solution: Maintain TCP connection pool
1069 -- Pool size: 10-20
1070 -- Idle timeout: 60 seconds
1071 -```
1072 -
1073 -### D. Security
1074 -
1075 -#### Encryption
1076 -- All streams: Encrypted with Noise protocol
1077 -- Forward secrecy guaranteed
1078 -
1079 -#### Authentication
1080 -- Automatic authentication with Peer ID
1081 -- Public key-based
1082 -
1083 -#### Authorization
1084 -- Current: All peers can connect
1085 -- Future: ACL (Peer ID-based)
1086 -
1087 ----
1088 -
1089 -## References
1090 -
1091 -### Official Documentation
1092 -- libp2p: https://docs.libp2p.io/
1093 -- GossipSub: https://github.com/libp2p/specs/tree/master/pubsub/gossipsub
1094 -- RelayDNS: https://github.com/gosuda/relaydns
1095 -
1096 -### Library Documentation
1097 -- Go libp2p: https://pkg.go.dev/github.com/libp2p/go-libp2p
1098 -- TypeScript libp2p: https://github.com/libp2p/js-libp2p
1099 -- Python libp2p: https://github.com/libp2p/py-libp2p
1100 -- Rust libp2p: https://docs.rs/libp2p
1101 -
1102 ----
1103 -
1104 -**Document Version**: 1.0.0
1105 -**Last Updated**: 2025-10-23
1106 -**Feedback**: https://github.com/gosuda/relaydns/issues
sdk/typescript/README.md deleted
-1
@@ -1 +0,0 @@
1 -# TypeScript SDK
\ No newline at end of file
sdk/typescript/a.ts