AI 资讯
Linux 7.1, tRPC's Query Overhaul, and Biome 2.0 Beta: What Developers Need to Know
This week's tooling landscape is quieter on the AI-native side but dense with infrastructure moves that affect how AI-driven workloads actually run in production. Cloudflare's Workflows scaling overhaul is the clearest signal: agent-triggered execution is now an assumed pattern, not a novelty, and platforms are rearchitecting accordingly. The rest of the week rounds out with a kernel maintenance drop, a meaningful abstraction removal in tRPC, and a Biome beta that's finally making ESLint replacement feel plausible. Linux 7.1 Released with Driver and Networking Fixes 7.1 is a maintenance release. No architectural changes, no new subsystems—just patches you should care about if you're running affected hardware or kernel-adjacent tooling. The two fixes worth flagging are heap overflows in the USB serial io_ti driver ( get_manuf_info() and build_i2c_fw_hdr() ), plus memory leak corrections scattered across drivers and networking subsystems. Trace tooling also gets updates, which matters if you're doing kernel-level performance analysis on production systems. One operational note: Torvalds is traveling, so merge window latency may be irregular. If you're tracking pull request timelines for custom kernel builds, plan for slippage. Verdict: Ship — if you're on 7.0 and running USB serial hardware or affected networking paths, upgrade on your normal kernel cycle. No breaking changes, no new dependencies, nothing to validate beyond your existing regression suite. tRPC Drops Abstraction Layer for React Query This is the kind of change that looks small in a changelog and feels large in daily development. The new tRPC client exposes native TanStack Query interfaces— QueryOptions and MutationOptions —directly, rather than wrapping them in tRPC-specific hooks. The practical effect: if you're already using TanStack Query elsewhere in your app, you stop context-switching between two similar-but-different mental models. You call .queryOptions() and .mutationOptions() factories and pa
AI 资讯
Use the Telegram Bot API in OpenClaw via Cloudflare WARP (1.1.1.1)
You run a Telegram bot through OpenClaw on your own Linux server. One day it goes quiet. The bot can't send or receive. But the server itself is fine — SSH works, apt works, other sites load. The reason: your server can't reach api.telegram.org . Some networks block or throttle it, so every call times out while everything else is fine. The clean fix: route only OpenClaw's Telegram traffic through Cloudflare WARP (1.1.1.1) . Everything else on the box stays direct and fast — including your SSH login. Here is the full setup, step by step. First, confirm it's a Telegram-only problem curl --max-time 8 https://api.telegram.org/ # hangs / times out curl --max-time 8 https://www.google.com/ # works instantly If Telegram times out but other sites are quick, this guide is for you. How it works We chain three small tools: OpenClaw ──▶ iptables ──▶ redsocks ──▶ WARP (SOCKS5) ──▶ Cloudflare ──▶ api.telegram.org WARP gives us a local proxy that exits through Cloudflare's network (which can reach Telegram). redsocks turns normal connections into proxy connections (so the app needs no proxy support — OpenClaw has none). iptables picks only OpenClaw's Telegram traffic and sends it to redsocks. The trick is in that last step. We match by the app's user and Telegram's IP ranges, so nothing else is touched. Step 1: Install WARP in proxy mode # Add Cloudflare's package repo curl -fsSL https://pkg.cloudflareclient.com/pubkey.gpg \ | gpg --yes --dearmor -o /usr/share/keyrings/cloudflare-warp-archive-keyring.gpg echo "deb [signed-by=/usr/share/keyrings/cloudflare-warp-archive-keyring.gpg] \ https://pkg.cloudflareclient.com/ $( lsb_release -cs ) main" \ > /etc/apt/sources.list.d/cloudflare-client.list apt-get update && apt-get install -y cloudflare-warp # Sign up (free) and switch to proxy mode warp-cli --accept-tos registration new warp-cli --accept-tos mode proxy # opens a SOCKS5 proxy on 127.0.0.1:40000 warp-cli --accept-tos connect Now check that WARP can reach Telegram: curl --socks5-
AI 资讯
The Hidden Linux Routing Issue That Broke My Deployment
The deployment should have taken a few minutes. The application was running, DNS was configured correctly, and the domain was already pointing to the server's public IP. Caddy was configured as a reverse proxy and was listening on ports 80 and 443. Every item on my deployment checklist appeared healthy. Yet every Let's Encrypt validation attempt kept failing. The error looked simple enough: authorization failed timeout during connect likely firewall problem At first, I believed it. I checked DNS resolution, verified firewall rules, confirmed that Caddy was listening on the expected ports, and made sure the application itself was reachable. Every check came back clean. That was the first clue that the problem might not be where the logs were pointing. The Obvious Things The first assumption was DNS. I verified that the domain resolved to the correct public IP. dig +short my-domain.com Everything looked correct. Next came the firewall. sudo ufw status Ports 80 and 443 were open. There were no unexpected deny rules, and nothing suggested inbound traffic was being blocked. Then I checked whether Caddy was actually listening. sudo ss -tulpn | grep -E ':80|:443' Again, everything looked normal. The application itself was healthy too. curl http://localhost:3001 returned a valid response. At this point I had checked most of the things engineers typically check when certificate validation fails. DNS looked good, the firewall looked good, the reverse proxy was healthy, and the application was running. Yet the validation errors continued. The Part That Sent Me In The Wrong Direction The error messages kept mentioning connectivity problems and possible firewall issues. That wording influenced my thinking more than it should have. I spent time investigating firewall rules, reverse proxy configuration, TLS settings, and domain configuration. Every new hypothesis felt reasonable, but none of them explained why local tests consistently succeeded while external validation continued
AI 资讯
How to Use Claude to Troubleshoot Linux Servers
Claude is genuinely useful for production Linux troubleshooting — when you use it right. Here's the workflow that works, after a year of using it on real incidents across Ubuntu, RHEL, and Rocky. The mental model: Claude is a senior pair, not an oracle The mistake most engineers make on day one: they paste a 5-line error message and expect a fix. Claude can do better than that — but only if you give it the same context you'd give a senior engineer joining your incident bridge. A senior engineer would want: What OS and version? What does this server do? What changed recently? What's the actual symptom? What command output have you already gathered? Give Claude that, and the quality of analysis changes completely. The workflow Step 1: Establish context with a system prompt Use our Linux Server Troubleshooting Prompt as your system prompt, or paraphrase: "You are a senior Linux sysadmin. Rank root-cause hypotheses by probability. Recommend safe diagnostics first. Label destructive commands as DANGEROUS." Step 2: Paste structured context, not noise Good: OS: Ubuntu 22.04, kernel 5.15 Role: production MySQL replica, 64GB RAM, 16 cores Recent changes: kernel upgrade 6 hours ago Symptom: server load average 40+, MySQL replication lag growing, queries timing out $ uptime 14:22:01 up 6:02, 4 users, load average: 41.23, 38.51, 35.04 $ free -h total used free shared buff/cache available Mem: 62Gi 58Gi 1.2Gi 128Mi 3.1Gi 1.8Gi $ iostat -xz 2 3 [...] Bad: my server is slow can you help Step 3: Let it ask follow-up questions The good prompts in our library tell Claude to ask for missing data before guessing. When it asks "can you share dmesg | tail -50 and vmstat 1 5 ?" — that's a feature, not a flaw. Give it the data. Step 4: Validate suggested commands before running Claude will sometimes suggest a command with subtly wrong syntax, a destructive flag, or a path that doesn't exist on your distro. Read every suggestion before running. Never paste straight into a root shell. Step 5
AI 资讯
From Mint to NixOS: Why a Long-Time Linux User Made the Switch
Background I started daily driving Linux back in 2019. The start of that journey was rough, and I still deeply appreciate the help I received in those early days from the old guard who kept me moving forward. Early on, I quickly found my home with Linux Mint and its Cinnamon desktop. As the saying goes, "You don't choose a Linux desktop; the desktop chooses you." Built on top of a stable foundation with a rich package infrastructure, Cinnamon provided a familiar experience that bridged the gap from Windows. It also afforded me excellent customization options right out of the box, such as configuring custom keyboard shortcuts or setting up auto-login startup scripts, while always getting out of my way. No adverts, no pop-ups, just a fast and efficient desktop environment. I won't lie, though: I distro-hopped multiple times just to see if the grass was greener. Through those escapades, I quickly realized I am definitely not a GNOME person; I do not like polyfilling my desktop experience with a suite of extensions. And as much as I appreciate KDE Plasma, I learned that with great customization comes great responsibility because it was far too easy for me to break my environment with just a few theme toggles. This is not a dig at those desktop environments; it just means I am not wired for that kind of experience. As I continued my Linux journey, my priorities shifted. I wanted a predictable operating system that could act as a trusted companion, both for my daily life as a software developer and as a casual user wanting to watch Netflix on the weekends. This is what made me appreciate Linux Mint even more. It featured a predictable release cycle, a stable package base built on Ubuntu LTS, and Timeshift to guard against system breakage during upgrades. However, two major friction points always bothered me: Stable but Stale Packages: Linux Mint's software is incredibly stable, but it is rarely fresh. For example, the okular package is consistently several versions behind
AI 资讯
The Only Productivity Hack That Actually Worked for Me
The Only Productivity Hack That Actually Worked for Me I've tried every website blocker in existence. They all have the same flaw: one click and they're off. That settings toggle might as well not exist when the urge to procrastinate hits. I needed something I couldn't override. So I built the opposite. The Problem Every blocker follows the same pattern: it blocks, you unblock, you procrastinate. The issue isn't discipline — it's that your future self and your present self want different things. And that future self will happily undo anything you set up. What I needed was a system where both selves agreed on the rules upfront and then neither could break them. The Solution kblocker is a Linux kernel module that hooks into netfilter and drops TCP connections to whatever sites I configure. The key feature isn't the blocking — it's how you turn it off. When blocking is enabled, kblocker generates a 128-bit key. With PGP mode, it automatically encrypts that key to people I trust and then erases it from kernel memory. The raw key no longer exists anywhere on my system. To disable the blocker, one of those people has to decrypt it and send it back to me. I outsourced my willpower. When I want to focus, I run: sudo kblockerctl enable 120 Two hours of blocked distractions. If I feel the urge to procrastinate, I can't — I'd have to text a friend, explain why, wait for them to decrypt it, and paste the result. By then the urge is gone. The Result I've gone from losing entire afternoons to YouTube to actually finishing things. The blocker has caught me mid-reflex to type youtube.com more times than I can count. It's free if anyone wants it: github.com/Dan-J-D/kblocker If you keep breaking your own focus tools, this is for you.
AI 资讯
OS Architecture, Kernel, Shell & File System
🐧 Linux for DevOps — Session 2: Understanding the Kernel, Shell, OS Architecture & File System 📓 Learning in public — These are my personal notes from my Linux for DevOps & Cloud journey. I'm sharing them in a way that's easy to revisit later and hopefully useful for anyone else starting out. In the previous session, I got comfortable with Linux basics and terminal access. This session focused on understanding what actually happens behind the scenes when we run commands , how Linux is structured internally, and how files are organized on the system. These concepts might sound theoretical at first, but they're the foundation of everything you'll do in DevOps—from managing EC2 instances and Docker containers to troubleshooting production servers. The Linux Kernel: The Heart of the Operating System The kernel is the most important component of Linux. Think of it as a translator sitting between software and hardware. Applications can't directly talk to the CPU, RAM, disks, or network interfaces. Instead, every request goes through the kernel. When you run a command, open a browser, start a Docker container, or deploy an application, the kernel is responsible for making it happen. Its main responsibilities include: Responsibility Purpose Resource Management Decides which process gets CPU time Memory Management Allocates and releases RAM Process Management Creates, schedules, and terminates processes Device Management Communicates with hardware through drivers Without the kernel, Linux would simply be a collection of files with no way to interact with hardware. Types of Kernels Not every operating system uses the same kernel design. Monolithic Kernel (Linux) keeps most operating system services inside a single kernel space. This approach is extremely fast because components communicate directly. Microkernel keeps only essential functionality in kernel space and moves other services outside. This improves isolation and stability but introduces additional overhead. Hybrid K
AI 资讯
Rebuilding the Hull at Sea
The box that ran everything started dying in April. Not dramatically. Machines almost never die dramatically. It started with instability... the kind you explain away once, side-eye twice, and start losing sleep over the third time production goes down while you're in the middle of something else. The host under my entire stack... public site, analytics, security tooling, the AI crew's memory layer... was getting flaky. And flaky hardware only trends one direction. Here's the thing about a homelab that lives in a 40ft fifth wheel: there is no second team. No vendor escalation. No change advisory board. No maintenance window negotiated three weeks out. There's me, a crew of governed AI instances, and a reclaimed Dell T3600 about to get the biggest promotion of its second life. So we didn't try to heal the sick box. We built a new hull alongside it and started moving the ship... plank by plank... while it was still sailing. One ground rule, set day one: the old host stays untouched and keeps serving production until the new hull is proven. Not "mostly proven." Proven. Hold that thought, it matters at the end. Moving containers is the easy part. Docker made that boring years ago, and boring is a compliment in infrastructure. What's never boring is the inventory of everything you assumed and never wrote down. A migration doesn't test your stack. It tests your assumptions. Here's what mine were hiding. 01: The umbilical nobody documented Security stack went first. Suricata, Zeek, Wazuh, CrowdSec, Falco, the whole alphabet, up clean on the new hull. Then the MCP server, the piece that gives the AI crew its hands, refused to come up right. It was hard-wired over HTTP to the crew's memory backend. A live dependency, in production for months, documented exactly nowhere. The crew that documents every f*cking thing had never documented its own umbilical cord. Fix was trivial once we could see it: deploy the brain before the hands. Reorder, redeploy, done. But the lesson isn't
AI 资讯
Stop Hand-Editing Fragile APT Lines: Practical deb822 `.sources` Files for Debian and Ubuntu
If you still manage APT repositories as long one-line deb ... entries, you are working with a format APT now explicitly marks as deprecated. It still works, but it is harder to read, harder to automate safely, and easier to get wrong when you add options like arch= or signed-by= . The better option is deb822 style .sources files. This post shows how to: read the structure of a .sources file migrate a legacy .list entry safely use Signed-By without falling back to apt-key disable a repository cleanly without deleting it verify that APT accepts the new configuration I am focusing on practical host administration, not packaging theory. Why move to deb822 now? The sources.list(5) man page now says the traditional one-line .list format is deprecated and may eventually be removed, though not before 2029. More importantly, deb822 solves real operational annoyances: fields are explicit instead of positional one stanza can describe multiple suites or types Enabled: no is cleaner than commenting lines in and out machine parsing is much easier Signed-By is clearer and safer in structured form On a current Debian host, you may already be using it without noticing: find /etc/apt/sources.list.d -maxdepth 1 -type f -name '*.sources' On my test system, the default Debian repository is already stored as /etc/apt/sources.list.d/debian.sources . The old format vs the new format A traditional one-line entry looks like this: deb [arch=amd64 signed-by=/etc/apt/keyrings/example.gpg] https://packages.example.com/apt stable main The same source in deb822 format becomes: Types: deb URIs: https://packages.example.com/apt Suites: stable Components: main Architectures: amd64 Signed-By: /etc/apt/keyrings/example.gpg That is the core win. Instead of cramming everything into one line and hoping spacing stays correct, each field says exactly what it means. Example 1, a clean Debian .sources file Here is a practical example for Debian using separate stanzas for the main archive and the security arch
AI 资讯
Nix Series: Basic Nix Language
Pada series sebelumnya, kita sudah melakukan instalasi nix di VirtualBox dan setup SSH agar dapat diakses diluar VirtualBox. Sebelum kita lanjut untuk melakukan konfigurasi system lagi, kita butuh mengetahui bagaimana syntax dalam menulis program Nix dan di artikel ini kita akan mempelajari dasar syntax-nya. Nix Language Nix adalah purely functional language yang lazy-evaluated , digunakan untuk mengkonfigurasi Nix package manager dan NixOS. Karakteristik utama: Purely functional : sebuah function hanya bisa mengembalikan nilai berdasarkan inputnya, tidak bisa mengubah variabel di luar scope-nya (no side effects), dan tidak ada variabel yang bisa diubah setelah didefinisikan (no mutation). Kalau kamu familiar dengan const di beberapa bahasa pemrograman, semua variabel di Nix berperilaku seperti itu. Lazy evaluation : Nix tidak menghitung nilai suatu ekspresi sampai nilai itu benar-benar dibutuhkan. Ini artinya kamu bisa mendefinisikan ribuan package di nixpkgs tanpa semuanya dievaluasi sekaligus. Hanya yang kamu gunakan saja yang akan diproses. Semua adalah expression : tidak ada statement di Nix, setiap baris kode selalu menghasilkan sebuah nilai. if/else bukan statement seperti di bahasa pemrograman pada umumnya, melainkan expression yang harus mengembalikan nilai dari kedua cabangnya. Tidak ada loops : karena variabel tidak bisa diubah, loop seperti for atau while tidak ada artinya di Nix. Sebagai gantinya, kamu menggunakan fungsi seperti map dan filter , atau rekursi untuk mengolah kumpulan data. 1. Basic Data Type Konsep JavaScript Nix String "hello" "hello" Number 42 , 3.14 42 , 3.14 Boolean true , false true , false Null null null List [1, 2, 3] [ 1 2 3 ] Object { a: 1 } { a = 1; } ⚠️ Perbedaan Penting List di Nix menggunakan spasi sebagai pemisah, bukan koma Attribute set menggunakan = bukan : , dan setiap entry diakhiri dengan ; Nix let name = "Alice" ; age = 30 ; scores = [ 10 20 30 ]; person = { name = "Bob" ; age = 25 ; }; in person Javascript const name
AI 资讯
I Built a Git Sync Tool for My Obsidian Vault
I Built a Git Sync Tool for My Obsidian Vault You write notes, you save them, you forget to push to GitHub. Then your laptop dies, and your notes are gone. I built a single Bash script that automates the entire sync workflow, and it works with any Git repo. If you use Obsidian (or any plain-text note-taking system) and sync via Git, you know the drill: write notes, stage changes, commit, fetch, check status, pull, push. Every time. It's 6 repetitive commands that you will inevitably skip until disaster strikes. I got tired of this and built git-sync , a single Bash script that does everything in one go. What It Does git-sync is a terminal-based Git sync tool that: Auto-commits all changes with a timestamp Fetches remote state Detects divergence (ahead/behind) Shows you only the relevant sync options Executes your choice with safety guard rails How It Works Run it from inside any Git repo: ./git-sync Phase 1 - Auto-commit: Staged or unstaged changes are committed automatically with a message like "Last Sync: Jun-12 (Arch)" . The device name is configurable. Phase 2 - Fetch & Detect: It fetches from remote, counts how many commits ahead and behind you are, and categorises the state: ahead, behind, diverged, or in-sync. Phase 3 - Smart Menu: Only relevant options are shown: State Options Ahead only Upload, Sync, Force push, Cancel Behind only Download, Sync, Hard reset, Cancel Diverged All six options Phase 4 - Execute: The chosen action runs with a spinner and status messages. Destructive operations (force push, hard reset) require explicit confirmation. Why It's Useful for Notes Syncing Obsidian + Git is a powerful combo. Your notes are plain markdown, version-controlled, accessible from any device. The friction is the sync ritual. git-sync removes it. Multi-device workflows: I run this on my Arch desktop (DEVICE_NAME="Arch") and my work laptop (DEVICE_NAME="Laptop"). The auto-commit message tells me exactly which machine made each sync, so I can trace conflicts back
AI 资讯
Recovering data from a failed RAID array with ddrescue: a practical walkthrough
When a RAID array fails, the worst thing you can do is panic and start poking at it immediately. I've seen too many cases where an impatient rebuild attempt overwrote the only good copy of data. This walkthrough covers how to safely approach a degraded or failed RAID — with ddrescue as your best friend. Step 0: Stop. Don't touch the array yet. Before running mdadm --assemble , before doing anything, clone your physical disks . A RAID 5 with one failed drive can lose everything the moment a second drive throws a read error during rebuild. This isn't hypothetical — it's how most total RAID losses happen. The golden rule: image first, recover second . Step 1: Assess the damage # Check current RAID state cat /proc/mdstat # More detail mdadm --detail /dev/md0 Look for: [UUU_] — one drive failed (underscore = missing) [UU__] — two drives failed (catastrophic for RAID 5) State: degraded , recovering , or failed Do NOT run mdadm --manage /dev/md0 --add /dev/sdX yet. Stop the array instead: mdadm --stop /dev/md0 Step 2: Clone each disk with ddrescue ddrescue is the right tool because it handles read errors gracefully: it maps bad sectors, retries them, and lets you resume interrupted sessions. Never use dd for a failing disk. Install it: # Debian/Ubuntu sudo apt install gddrescue # RHEL/CentOS sudo dnf install ddrescue Clone each RAID member to a separate image file (you need enough storage — same total size as all disks combined): # First pass: copy everything readable, skip bad sectors fast sudo ddrescue -d -r0 /dev/sda /mnt/backup/sda.img /mnt/backup/sda.log # Second pass: retry bad sectors up to 3 times sudo ddrescue -d -r3 /dev/sda /mnt/backup/sda.img /mnt/backup/sda.log Key flags: -d — direct disk access (bypass kernel cache) -r0 / -r3 — retry bad sectors 0 or 3 times The .log mapfile is critical: it lets you resume if the clone is interrupted Repeat for every disk in the array ( sdb , sdc , etc.). Step 3: Work from the images Once you have image files, assemble a soft
产品设计
High-severity vulnerability in Linux caused by a single errant character
Use-after-free bug can be exploited to evade sandbox defenses.
AI 资讯
Learning DevOps from First Principles: What an EC2 Instance Actually Is
One of the first cloud concepts many people encounter while learning AWS is EC2 . The name sounds technical. The documentation is extensive. And the number of configuration options can make it feel like something fundamentally different from a regular computer. But while trying to understand cloud computing, I found myself repeatedly coming back to a simple thought: At the end of the day, an EC2 instance is just another computer. That realization helped me understand cloud infrastructure much more clearly. The Intimidation Factor When people first open the AWS console, they encounter terms such as: EC2 VPC Security Groups Elastic IPs Auto Scaling It is easy to feel that cloud computing is an entirely different world. But before diving into those concepts, it helps to ask a simpler question: What is an EC2 instance actually providing? Starting with the Name EC2 stands for: Elastic Compute Cloud The important word here is: Compute AWS is essentially renting computing resources. When you launch an EC2 instance, AWS allocates: CPU Memory (RAM) Storage Networking to a virtual machine that you can access. In other words: You are renting a computer that lives inside AWS's infrastructure. Comparing It to a Personal Computer Consider a typical laptop. It contains: A processor RAM Storage An operating system Network connectivity Now consider an EC2 instance. It also contains: Virtual CPUs RAM Storage An operating system Network connectivity The location is different. The concepts are the same. The Main Difference: Ownership The biggest difference is not technical. It is operational. With a personal computer: You own the hardware. The machine sits near you. You maintain it. With EC2: AWS owns the hardware. The machine runs in a data center. AWS manages the physical infrastructure. You only manage the virtual machine running on top of it. Why Linux Knowledge Transfers This was one of the most interesting observations during my learning. If an EC2 instance runs Linux, many of th
AI 资讯
Same Hardware, Different Experience: Why Linux Feels Faster
A few weeks after switching from Windows to Linux, I noticed something interesting. The hardware had not changed. The processor was the same. The RAM was the same. The SSD was the same. And yet, the laptop felt noticeably faster. Not necessarily because applications were completing tasks dramatically quicker, but because the entire system felt more responsive. Keyboard input felt immediate. Windows opened faster. Terminal commands appeared instantly. The desktop experience felt smoother. This raised a question: How can the same hardware feel different simply because the operating system changed? While I'm still learning, this is the mental model I've built so far. The Hardware Didn't Change Consider a laptop with: AMD Ryzen processor 16 GB DDR5 RAM NVMe SSD Modern integrated graphics When switching operating systems, none of these components change. The CPU does not suddenly become faster. The RAM does not magically increase. The SSD remains identical. From a hardware perspective: ```text id="u3m9xd" Before → Same Hardware After → Same Hardware So the difference must come from somewhere else. --- ## An Operating System Is Not Just a User Interface Many people think of an operating system primarily as the desktop they see. But an operating system does far more than display windows and icons. It manages: * Memory * CPU scheduling * Processes * Storage * Networking * Device drivers * Background services In other words: > The operating system decides how hardware resources are used. Two operating systems can therefore create very different experiences using the same hardware. --- ## Perceived Performance vs Raw Performance One thing I have learned is that performance is not always about benchmarks. A system can have excellent benchmark scores and still feel sluggish. Why? Because users experience responsiveness, not benchmark numbers. Examples include: * How quickly a window opens * How fast a menu appears * How responsive typing feels * How quickly applications launch
AI 资讯
Learning DevOps from First Principles: MAC Addresses vs IP Addresses — The Difference Finally Clicked
One of the first networking concepts that confused me was this: Why does a computer need both a MAC address and an IP address? At first glance, they seem to solve the same problem. Both appear to identify a device. Both show up in networking tools. Both appear in packet captures. So why do we need two different addresses? While exploring Linux networking tools and Wireshark, the distinction finally started making sense. This article summarizes the mental model that helped me understand the difference. Looking Inside the Machine Before discussing addresses, it helps to understand where they come from. If you open a typical laptop, you will usually find components such as: Battery RAM Storage Processor Cooling system Network interfaces One of those network interfaces is typically: A Wi-Fi card An Ethernet controller These components are responsible for network communication. They are the parts of the machine that actually send and receive data across a network. Every Network Interface Has an Identity A network interface needs a way to identify itself. This is where the MAC address comes in. A MAC address is associated with a network interface card (NIC). Example: ```text id="q3d9nm" 2C:9C:58:8B:2D:7B Think of it as the identity of the network interface itself. Not the operating system. Not the browser. Not the application. The network hardware. --- ## What Is a MAC Address? MAC stands for: **Media Access Control** A MAC address operates at the **Data Link Layer** of the OSI model. Its primary purpose is to help devices communicate within a local network. Examples include: * Laptop to router * Router to switch * Switch to printer In other words: > MAC addresses help devices find each other on the same local network. --- ## What Is an IP Address? An IP address serves a different purpose. Example: ```text id="g8x4tc" 192.168.1.20 or ```text id="v6u7mz" 2405:201:8000::1 IP addresses operate at the **Network Layer**. Their job is to identify where a device exists within a
AI 资讯
Run Gemma-4 12B on WSL2 with llama.cpp
1. update WSL environment sudo apt update && sudo apt upgrade -y 2. install dependencies If you don't use -hf option, you don't need to install libssl-dev in this step. sudo apt install build-essential cmake git libssl-dev -y If nvidia-smi shows a GPU/GPUs on your terminal, you will need to install the tooklit. This will take some time. sudo apt install nvidia-cuda-toolkit -y 3. clone the repo Build llama-cli and llama-server. This step also will take some time. If you don't plan to use -hf option, you don't need to use -DLLAMA_OPENSSL=ON . git clone https://github.com/ggerganov/llama.cpp cd llama.cpp cmake -B build -DGGML_CUDA = ON -DLLAMA_OPENSSL = ON cmake --build build --config Release # no GPU git clone https://github.com/ggerganov/llama.cpp cd llama.cpp cmake -B build cmake --build build --config Release 4. run the model Run gemma-4-12b-it with cli and server. unsloth/gemma-4-12b-it-GGUF · Hugging Face We’re on a journey to advance and democratize artificial intelligence through open source and open science. huggingface.co ./build/bin/llama-cli -hf unsloth/gemma-4-12b-it-GGUF:UD-Q4_K_XL > hello [ Start thinking] The user said "hello" . The user is initiating a conversation. Respond politely and offer assistance. * "Hello! How can I help you today?" * "Hi there! What's on your mind?" * "Hello! Is there anything I can assist you with?" [ End thinking] Hello! How can I help you today? [ Prompt: 19.5 t/s | Generation: 11.8 t/s ] or run web-ui ./build/bin/llama-server -hf unsloth/gemma-4-12b-it-GGUF:UD-Q4_K_XL --port 8080 optional download model from huggingface mkdir -p models wget -O models/gemma-4-12b-it-UD-Q4_K_XL.gguf https://huggingface.co/unsloth/gemma-4-12b-it-GGUF/resolve/main/gemma-4-12b-it-UD-Q4_K_XL.gguf
AI 资讯
Install PHP 8.5 with ASDF on Arch Linux
This quick tutorial shows how to install ASDF Version Manager on Arch Linux and use it to install PHP 8.5. Install Required Dependencies First, install the required packages and build dependencies: yay -S base-devel libpng postgresql-libs re2c gd oniguruma libzip libsodium You may also want to install additional common dependencies: yay -S curl git openssl zlib libxml2 sqlite Install ASDF Clone the ASDF repository: git clone https://github.com/asdf-vm/asdf.git ~/.asdf --branch v0.18.0 Add ASDF to your shell configuration. Bash echo '. "$HOME/.asdf/asdf.sh"' >> ~/.bashrc echo '. "$HOME/.asdf/completions/asdf.bash"' >> ~/.bashrc source ~/.bashrc ZSH echo '. "$HOME/.asdf/asdf.sh"' >> ~/.zshrc echo '. "$HOME/.asdf/completions/asdf.bash"' >> ~/.zshrc source ~/.zshrc Verify installation: asdf --version Add the PHP Plugin Install the PHP plugin for ASDF: asdf plugin add php https://github.com/asdf-community/asdf-php.git Install PHP 8.5 List available PHP versions: asdf list all php Install PHP 8.5: asdf install php 8.5.0 Set PHP 8.5 as the global default: asdf global php 8.5.0 Reload your shell: exec $SHELL Verify the installation: php -v Expected output: PHP 8.5.x ( cli ) Useful ASDF Commands List installed PHP versions: asdf list php Install another PHP version: asdf install php 8.4.0 Switch globally: asdf global php 8.4.0 Switch locally for a project: asdf local php 8.5.0 Optional: Install Composer After installing PHP, install Composer globally: php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');" php composer-setup.php sudo mv composer.phar /usr/local/bin/composer rm composer-setup.php Verify: composer --version
AI 资讯
The token bill comes due: Inside the industry scramble to manage AI’s runaway costs
"The whole conversation shifted from tokenmaxxing and 'go fast' to 'we need guardrails, how do we control this?'"
AI 资讯
Docker on Proxmox LXC: What Actually Works (and Why Unprivileged Doesn't)
The Setup I run a Proxmox 9 homelab (pve-manager/9.0.5, kernel 6.14.8-2-pve) and I needed to run Docker inside an LXC container — not a VM — to test a customer-style "bring-your-own-VPS" deployment path for a PaaS I'm building. The container had to act like a standard Ubuntu cloud VM: Docker, systemd, the works. LXC over a full VM gets me near-bare-metal performance, a fraction of the RAM overhead, and instant boots. The catch: the "Docker on LXC" recipes you'll find on most blog posts and Proxmox forum threads are out of date . They assume kernel 5.x and runc 1.1.x. On a modern Proxmox (kernel 6.14 + runc 1.2+ shipped with Docker 29) those recipes fail in two new and confusing ways before you even reach the workarounds we used to know about. This article walks through exactly what fails, why it fails, and the config that actually works in 2026 — plus an honest look at the security tradeoffs, because spoiler: the working config is privileged , and that matters. The Goal A Proxmox LXC container that can: Run docker run hello-world cleanly Pull and build complex images (multi-stage builds, overlay2 storage driver) Run nested containers with their own systemd Use systemd --user for per-service lingering processes Attempt 1: Unprivileged LXC (the path you "should" take) Conventional wisdom says: use unprivileged LXC. The container's root is mapped to an unprivileged UID on the host (typically 100000 ), so even a full container compromise can't escape to host root. Modern Proxmox makes this the default and recommended mode. I started with an unprivileged Ubuntu 25.04 container, added the now-standard features: pct set <vmid> -features nesting = 1,keyctl = 1,fuse = 1 Then inside the container, installed Docker from the official download.docker.com repo and ran: docker run --rm hello-world Here's what happened: docker: Error response from daemon: failed to create task for container: failed to create shim task: OCI runtime create failed: runc create failed: unable to start