#! /usr/bin/env python3
import argparse
import sys
import logging
import ipaddress
import hashlib
import base64

logger = logging.getLogger(__name__)


def main() -> int:
    # Handle program arguments
    ap = argparse.ArgumentParser(
        prog="wg-peer-to-ipv6",
        description="Deterministically generate IPv6 addresses from WireGuard public keys",
    )
    ap.add_argument("prefix", help="IPv6 prefix", type=ipaddress.IPv6Network)
    ap.add_argument("public_key", help="WireGuard public key")
    ap.add_argument(
        "-v", "--verbose", help="Enable verbose logging", action="store_true"
    )
    args = ap.parse_args()

    # Configure logging
    logging.basicConfig(
        level=logging.DEBUG if args.verbose else logging.INFO,
        format="%(levelname)s:	%(message)s",
    )
    
    # Decode the public key
    public_key = base64.b64decode(args.public_key)
    
    # Hash the public key
    hash = hashlib.sha256(public_key).digest()
    
    # Figure out how many bits we have for the host part
    host_bits = args.prefix.max_prefixlen - args.prefix.prefixlen
    
    # Take that many bits from the hash
    host = int.from_bytes(hash, "big") >> (256 - host_bits)
    
    # Create the IPv6 address
    ipv6 = args.prefix.network_address + host
    
    print(ipv6)

    return 0


if __name__ == "__main__":
    sys.exit(main())