FROM golang:1.25-alpine3.22 AS build
RUN mkdir /opt/build
WORKDIR /opt/build

RUN apk add git make gcc musl-dev

# Build specmon
RUN git clone https://github.com/specmon/specmon.git
RUN cd specmon && git checkout 6db8f7449ed7f9edf1a82b96f301a219c4d2e4d5
WORKDIR /opt/build/specmon
RUN go mod tidy
RUN go build .

WORKDIR /opt/build

#ENV GOEXPERIMENT=greenteagc,jsonv2

# Build go-annotate
RUN git clone https://github.com/specmon/go-annotate
RUN cd go-annotate && git checkout 5a827ad8b7beb96cc422f393ea20d8ee213c4290
WORKDIR /opt/build/go-annotate
RUN go mod tidy
RUN go build .
WORKDIR /opt/build

# Annotate the golang.org/x/crypto module
RUN git clone https://go.googlesource.com/crypto x-crypto
# RUN cd x-crypto && git checkout 349231f7e4e437ea89847c5dfce63eed67949f86
RUN cd x-crypto && git checkout 9290511cd23ab9813a307b7f2615325e3ca98902
RUN /opt/build/go-annotate/go-annotate -w -package -exported -import 'github.com/specmon/go-annotate/log' x-crypto/**/*.go
WORKDIR /opt/build/x-crypto
COPY modules/patches/blake2s.patch .
RUN git apply blake2s.patch
COPY modules/patches/chacha20poly1305.patch .
RUN git apply chacha20poly1305.patch
WORKDIR /opt/build

# Annotate the golang.org/x/net module
RUN git clone https://go.googlesource.com/net x-net
# RUN cd x-net && git checkout 49bf2d7d0528227391e641546af98c43047d22ab
RUN cd x-net && git checkout 2dab271ff1b7396498746703d88fefcddcc5cec7
RUN /opt/build/go-annotate/go-annotate -w -package -exported -import 'github.com/specmon/go-annotate/log' x-net/**/*.go
RUN find x-net -name "*.go" -exec sed -i 's|"golang.org/x/net|"github.com/specmon/x/net|g' {} \;
WORKDIR /opt/build/x-net
COPY modules/patches/ipv4_batch.patch .
RUN git apply ipv4_batch.patch
WORKDIR /opt/build

# Annotate the crypto module in the standard library
RUN wget https://github.com/golang/go/archive/refs/tags/go1.21.4.tar.gz
RUN tar -xzf go1.21.4.tar.gz
RUN cp -r go-go1.21.4/src/crypto std-crypto
WORKDIR /opt/build/std-crypto
RUN rm -rf .git && git init
COPY modules/patches/fix_internal_module.patch .
RUN git apply fix_internal_module.patch
RUN go mod init "github.com/specmon/std/crypto"
WORKDIR /opt/build
RUN find std-crypto -name "*.go" -exec sed -i 's|"crypto|"github.com/specmon/std/crypto|g' {} \;
RUN /opt/build/go-annotate/go-annotate -w -package -exported -import 'github.com/specmon/go-annotate/log' std-crypto/**/*.go

# build wireguard-go
RUN git clone https://git.zx2c4.com/wireguard-go
WORKDIR /opt/build/wireguard-go
RUN git checkout 12269c2761734b15625017d8565745096325392f
RUN find . -name "*.go" -exec sed -i 's|"crypto|"github.com/specmon/std/crypto|g' {} \;
RUN find . -name "*.go" -exec sed -i 's|"golang.org/x/net|"github.com/specmon/x/net|g' {} \;
RUN go mod edit -replace=github.com/specmon/go-annotate=../go-annotate
RUN go mod edit -replace=github.com/specmon/x/net=../x-net
RUN go mod edit -replace=golang.org/x/crypto=../x-crypto
RUN go mod edit -replace=github.com/specmon/std/crypto=../std-crypto
RUN go mod tidy
RUN make
#---------------------------------------------------
FROM alpine:3.22 AS main

WORKDIR /opt

RUN apk add python3 py3-pip wireguard-tools coreutils netcat-openbsd gcc 

COPY --from=build /opt/build/specmon/specmon /usr/bin
COPY --from=build /opt/build/wireguard-go/wireguard-go /usr/bin

COPY scripts/generate-keys.sh ./
RUN chmod +x ./generate-keys.sh
# Generate 1000 client keys
RUN ./generate-keys.sh 1000 /etc/wireguard

COPY monitor/go-rewrite.spthy monitor/wireguard.spthy monitor/pre-trace.py monitor/pre-trace-client.py ./

# Install cbor2 package for CBOR support
RUN pip install --no-cache-dir cbor2 --break-system-packages

ARG START_SCRIPT=start.sh
ARG README=README.md

COPY docker/$START_SCRIPT ./start.sh
RUN chmod +x ./start.sh

COPY docker/$README ./README.md

CMD ["./start.sh"]
