<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[ZeroVector]]></title><description><![CDATA[Weekly logs from my path into cybersecurity — network analysis, hands-on Wireshark and Kali Linux labs, and the honest wins and mistakes along the way. Document]]></description><link>https://zerovector.hashnode.dev</link><image><url>https://cdn.hashnode.com/res/hashnode/image/upload/v1593680282896/kNC7E8IR4.png</url><title>ZeroVector</title><link>https://zerovector.hashnode.dev</link></image><generator>RSS for Node</generator><lastBuildDate>Mon, 14 Sep 2026 20:39:25 GMT</lastBuildDate><atom:link href="https://zerovector.hashnode.dev/rss.xml" rel="self" type="application/rss+xml"/><language><![CDATA[en]]></language><ttl>60</ttl><item><title><![CDATA[Week 9: NDP Watcher Got a Real SOC-Style Fix, Then I Went Back to Python Basics]]></title><description><![CDATA[Quick Hook / Week in Review
The best work this week happened in two dense sessions near the end — NDP Watcher picked up a live terminal UI and, more importantly, an actual fix for a false-positive pro]]></description><link>https://zerovector.hashnode.dev/week-9-ndp-watcher-got-a-real-soc-style-fix-then-i-went-back-to-python-basics</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-9-ndp-watcher-got-a-real-soc-style-fix-then-i-went-back-to-python-basics</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Mon, 07 Sep 2026 16:59:57 GMT</pubDate><content:encoded><![CDATA[<h2>Quick Hook / Week in Review</h2>
<p>The best work this week happened in two dense sessions near the end — NDP Watcher picked up a live terminal UI and, more importantly, an actual fix for a false-positive problem I'd flagged as a known limitation weeks ago. The middle of the week belonged almost entirely to math ahead of Thursday's tuition, and one day disappeared to gaming after college and tuition already ate the hours. It closed with an unexpected but sensible move: starting a proper Python fundamentals track on W3Schools, even while the actual tool keeps getting more advanced.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The week's first real technical push went into v0.4. I hit a <code>PermissionError</code> running the script without <code>sudo</code> and correctly reasoned it through as a raw-socket privilege issue rather than a bug in my own code — the kind of distinction that matters, since chasing a nonexistent code bug would've wasted real time. On top of the existing CSV logging, I added a <code>rich</code>-based live terminal table with color-coded alerts, using a <code>deque</code> to cap the on-screen view at the 15 most recent rows while the CSV file keeps the full, unbounded history underneath. Getting <code>sniff()</code>'s single-argument callback to work with my two-argument <code>handle_packet(pkt, live)</code> function meant properly internalizing <code>lambda</code> as a middleman — and understanding that the parameter name on either side of the colon is arbitrary, as long as both sides agree with each other. I also worked through why <code>.append((timestamp, event_type, source_mac, details))</code> needs two sets of parentheses — the outer pair for the function call itself, the inner pair to bundle the tuple — and learned that <code>init_log()</code> isn't there to make the file exist (opening in <code>"a"</code> mode does that automatically), it's there to guarantee the header row gets written first. Wanting to keep the CSV log out of version control led into <code>.gitignore</code> properly, plus <code>git rm --cached</code> for a file that was already being tracked before I excluded it.</p>
<p>The most interesting catch of that session wasn't code at all — it was a real environment bug I found independently. Log timestamps were coming out roughly 9 to 10 hours off, and I traced it correctly to the Kali VM's system clock or timezone rather than anything in the Python logic, using <code>date</code> and <code>timedatectl</code> to dig into it, with the actual root cause (wrong timezone versus NTP drift) still pending confirmation. I also noticed a truncated last row in one log file, likely from an interrupted <code>Ctrl+C</code> run mid-write — not fixed yet, just flagged as something to watch.</p>
<p>The next big session pushed the tool to v0.5, and this one mattered more than a version bump suggests. Earlier work had flagged a real weakness: the spoofing detection treated every IP-to-MAC mismatch the same way, which meant legitimate IPv6 privacy-extension address rotation could trigger false alerts. v0.5 fixes that properly by comparing mismatches against a 30-second time window (<code>SPOOF_WINDOW</code>) — a fast, suspicious conflict gets flagged as <code>ALERT_SPOOFING</code>, while a slow one that's more likely just a legitimate address change gets logged as <code>INFO_MAC_CHANGE</code> instead. That's a genuine design upgrade, not cosmetic polish, and it's the kind of SOC-relevant triage thinking — distinguishing what's urgent from what's just informational — worth stating directly in an interview as "I found and fixed a false-positive source in my own detection logic." Getting there meant working through <code>datetime</code> versus <code>timedelta</code> properly — one's a point in time, the other's a duration, and subtracting two <code>datetime</code> objects gives you a <code>timedelta</code> you can compare directly with <code>&lt;</code> and <code>&gt;</code>. I also clarified how <code>live.update(build_table())</code> actually works: <code>build_table()</code> rebuilds the entire table fresh from whatever <code>recent_events</code> currently holds, and <code>live.update()</code> just swaps the on-screen display to match, called once at the end of every packet-handling pass regardless of which NDP message type triggered it. Same session cleared up a smaller but genuinely useful point about <code>.gitignore</code> itself — the file is a normal tracked file, visible to anyone looking at the repo, but the content it excludes never gets uploaded at all. Existence being visible and content being private are two separate things, and conflating them would be an easy mistake to carry forward. I also scoped out an extended roadmap for the whole project, from v0.5 through v1.0 with a stretch goal of a web dashboard afterward — a deliberate choice to build this out properly rather than leave it minimal.</p>
<p>The week closed with a pivot I didn't see coming but makes sense: creating a W3Schools account and starting through Python Home, Python Intro, and Python Get Started, alongside some general coding practice. Going back to formal fundamentals while already deep into a working v0.5 tool isn't a contradiction — it's filling in the base underneath work that's already ahead of it.</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>The middle of the week went almost entirely to math. One day was mostly spent pushing v0.3 to GitHub and fighting with VS Code inside the VM acting strangely — no run button showing up, still unresolved by day's end — before math took over as the priority with tuition looming on Thursday. The day after that was math homework and problems only, with honestly no cybersecurity or project work at all. And Thursday itself was a full write-off on that front: college and tuition ate most of the day, and the remaining time went to gaming rather than anything productive. Three days in a row with the project barely touched is a real gap, even with legitimate reasons behind most of it.</p>
<h2>Focus for Next Week</h2>
<p>Actually test v0.5's two alert types properly — ideally by simulating a controlled spoofing scenario rather than waiting around for organic traffic to trigger it, since that's the only way to confirm both the fast <code>ALERT_SPOOFING</code> and slow <code>INFO_MAC_CHANGE</code> paths actually behave the way they're designed to. Nail down the timezone bug's real root cause and fix it properly instead of leaving it as a known oddity. And keep the W3Schools fundamentals track running in parallel with the NDP Watcher build rather than letting one crowd out the other — they're reinforcing each other more than competing for time.</p>
]]></content:encoded></item><item><title><![CDATA[Week 8: NDP Watcher Went From v0.1 to v0.3, and a YouTube Channel Got Its Name]]></title><description><![CDATA[Quick Hook / Week in Review
This is the week two separate things stopped being ideas and became real, versioned artifacts. NDP Watcher — my network anomaly detection tool — went from a broken environm]]></description><link>https://zerovector.hashnode.dev/week-8-ndp-watcher-went-from-v0-1-to-v0-3-and-a-youtube-channel-got-its-name</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-8-ndp-watcher-went-from-v0-1-to-v0-3-and-a-youtube-channel-got-its-name</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Sun, 30 Aug 2026 18:21:51 GMT</pubDate><content:encoded><![CDATA[<h2>Quick Hook / Week in Review</h2>
<p>This is the week two separate things stopped being ideas and became real, versioned artifacts. NDP Watcher — my network anomaly detection tool — went from a broken environment and an unsaved file all the way to a working v0.3 with actual spoofing-detection logic, three GitHub commits deep. And on the content side, a YouTube channel finally got a name, a full recording pipeline, and a real production setup, after a genuine identity crisis over what to call it. Not every day was clean, but the two threads that mattered both landed somewhere real by Sunday.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The NDP Watcher arc is the spine of this week, and it started rougher than it ended. Early on, a session that should have been about writing detection code turned into pure environment plumbing — I set up VS Code Remote-SSH from host to Kali VM successfully, but lost track of whether <code>ndp_watcher.py</code> had actually been saved before running Git commands on it. It hadn't. <code>git add</code> had nothing to stage, and both <code>commit</code> and <code>push</code> failed as a result. The real lesson wasn't the bug itself, it was the habit that came out of it: always verify a file physically exists with <code>ls -la</code> before trusting Git commands against it, instead of assuming a tab being open means it saved.</p>
<p>The environment kept fighting back the next day. Remote-SSH started crashing outright, and disabling <code>remote.SSH.useExecServer</code> didn't fix it, nor did uninstalling and reinstalling the extension — it would work briefly, then fail silently with no error output. Rather than keep sinking time into an unresolved SSH bridging issue, I diagnosed it as a host-side extension/core version mismatch and made the call to install VS Code directly on the Kali VM instead, skipping the bridge entirely. That's a legitimate pivot, not a failure — when a tool fights you for multiple rounds with nothing to show for it, changing the approach is the correct move, not giving up.</p>
<p>With the environment finally stable, v0.1 actually shipped. Getting there meant working through a genuine mystery: the script was producing no output at all. I confirmed the interface and permissions were fine by capturing raw traffic with scapy and seeing TCP and ARP packets come through, which told me the capture itself worked — the real issue was that the network's traffic was heavily IPv4 with IPv6 sitting idle. Forcing real IPv6 traffic with a <code>ping6</code> to a public address finally produced a live NS/NA exchange the script correctly captured and classified. On top of that, I hit a "Repository not found" error pushing to GitHub, traced it independently to a scoped Personal Access Token that had been reused from an earlier repo, generated a fresh one, and confirmed the fix by testing pushes across both repos several times over. Getting through that last stretch without further guidance, mid-troubleshoot, is exactly the kind of "figured it out under pressure" story worth remembering for interviews later.</p>
<p>From there the tool grew fast. v0.2 upgraded it from bare message-type labels to full field extraction — router lifetime and the M/O flags and advertised prefix from Router Advertisements, target addresses from Neighbor Solicitation/Advertisement exchanges — and I verified it end-to-end against my own network's real traffic: a 7200-second (2-hour) router lifetime, both flags off confirming a SLAAC-only network with no DHCPv6, and the advertised prefix matching my VM's actual assigned IPv6 address. Along the way I picked up how to tell MAC and IPv6 formatting apart at a glance, and that a MAC address's first three byte-pairs (the OUI) identify the vendor — <code>08:00:27</code> being VirtualBox's own prefix. I also wrote a full README covering the project's purpose, security rationale, usage, example output, and a version roadmap out to v1.0, which matters more than it sounds — a roadmap like that signals a deliberate, iterative build process to anyone skimming the repo later.</p>
<p>v0.3 is where the tool actually became a detector rather than just a parser. I added two in-memory dictionaries — one tracking known routers by MAC against their lifetime and prefix, one tracking known neighbors by IP against their owning MAC — and built the actual detection logic on top: first-time sightings get learned silently, repeat sightings get compared against the stored baseline, and alerts fire on prefix changes, zero-lifetime RAs (a denial-of-service pattern), or a MAC claiming an IP that's already tied to a different one (NDP spoofing). It ran cleanly end to end on live traffic on the first real attempt. This learn-once, alert-on-mismatch pattern is the same fundamental structure real network anomaly detection runs on, which is worth saying plainly rather than downplaying. I'm also carrying forward a known limitation on purpose rather than pretending it's not there: the baseline is in-memory only and resets every run, and it doesn't yet account for legitimate IPv6 privacy-extension address rotation, which could trigger false positives — flagged clearly as v0.4+ work rather than something to quietly ignore.</p>
<p>Alongside all of that, a smaller thread ran in parallel: getting comfortable with actual Git internals. I reviewed the full SSH setup sequence for GitHub properly — <code>ssh-keygen</code>, starting the agent and adding the key, copying the public key to GitHub, testing the connection with <code>ssh -T git@github.com</code>, then cloning — and locked in why SSH auth is preferred over HTTPS-with-password for this workflow in the first place.</p>
<p>The second big thread this week had nothing to do with NDP Watcher: standing up a YouTube channel for project and cybersecurity content. The name took real work to land on — I went through on-brand extensions of ZeroVector, generic security-term names, movie-thriller-style options, and an earlier favorite, "Tripwire," before settling on <strong>Working Theory</strong>, chosen specifically because it ties to actual self-identity rather than being another genre trope, and because an existing company already uses the Tripwire name in the security space. The tagline landed on "Nothing here is finished — just tested," which frames every video around testing and refining ideas in public rather than presenting polished conclusions. I also decided against an AI-generated profile picture or watermark in favor of a real photo — notebook, whiteboard, or terminal shots — for authenticity.</p>
<p>The technical production setup got real depth too. OBS Studio is installed and configured with a working Window/Display Capture source, 1080p resolution, 30fps for tutorial-style content, NVENC/x264 encoding, a 12–16k Kbps bitrate, and mp4 output, plus hotkeys for start/stop/pause and mic mute chosen specifically to avoid clashing with other apps' shortcuts. Audio took several passes to land on the right tool — starting from a simple wired/USB mic straight into OBS, through a phone-as-synced-recorder fallback using clap-sync, into turning a phone into a live virtual mic via WO Mic (which meant understanding its server/client split and the hotspot/Wi-Fi Direct nuance when the phone acts as its own access point), and comparing that against AndroidMic, AudioRelay (ruled out partly over its one-hour free-tier mic limit), and finally landing on <strong>Micstream</strong> for low-latency Opus-codec streaming, with its ad-supported free tier accepted as a fair tradeoff.</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>One day's morning and evening both got eaten by gaming instead of the planned work, which cut directly into what should have been productive blocks — worth naming plainly rather than folding into the day's technical wins. The channel name also went through several complete pivots before landing on Working Theory, which cost real time, even if it ended in a stronger, more honest choice than the first idea. Same with the audio setup — WO Mic got explored in real depth, hotspot handling and all, before ultimately getting replaced by Micstream. Not wasted effort exactly, but not the final answer either, and it's worth remembering that some research time won't survive contact with a better option found later.</p>
<h2>Focus for Next Week</h2>
<p>On NDP Watcher: handle the IPv6 privacy-extension rotation gap so it doesn't generate false positives, and — the more exciting one — actually simulate a spoofing attempt on the lab network to watch the v0.3 alert logic fire live. That's both a real validation step and a strong story for later interviews. On the channel side: get an actual test recording done instead of just the pipeline sitting configured and untested, and get the thumbnail, banner, and profile photo shot so the channel has a real face instead of just settings screens behind it.</p>
]]></content:encoded></item><item><title><![CDATA[Week 7: The Week the Tooling Finally Clicked]]></title><description><![CDATA[Quick Hook
This was the week where a lot of scattered pieces turned into actual infrastructure. I fixed my dev environment properly, went deep on DNS security, ran my first full Git workflow start to ]]></description><link>https://zerovector.hashnode.dev/week-7-the-week-the-tooling-finally-clicked</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-7-the-week-the-tooling-finally-clicked</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Mon, 24 Aug 2026 15:51:31 GMT</pubDate><content:encoded><![CDATA[<h2>Quick Hook</h2>
<p>This was the week where a lot of scattered pieces turned into actual infrastructure. I fixed my dev environment properly, went deep on DNS security, ran my first full Git workflow start to finish, built my own shell commands by debugging real errors instead of copy-pasting fixes, and closed the week with a hands-on network build in Packet Tracer. Only one day was a true write-off, and even the slower day still had real math work behind it. This is the most technically dense week I've logged yet.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The week opened by fixing the boring-but-essential stuff: my actual dev environment. I confirmed VS Code on the host connecting via Remote-SSH into Kali is the standard professional setup, and my existing SSH config already supported it without changes. Getting Fastfetch and a Tokyo Night theme working seemed simple until the terminal color scheme turned into a real debugging chain — I assumed the wrong folder for QTerminal's color schemes, then a download silently landed in a <code>qtermwidget5</code> path instead of <code>qtermwidget6</code>, then a second source URL 404'd outright. The actual fix only came from diffing <code>find / -iname "*.colorscheme"</code> output against <code>qterminal.ini</code>'s real <code>colorScheme=</code> value, which showed the system-wide schemes live in <code>/usr/share/qtermwidget6/color-schemes/</code>, not the user-level path I'd assumed. The lesson that stuck: when the same error keeps showing up after several different fixes, it's often not the same bug at all — worth checking actual file paths and config state directly instead of retrying variations of a guess.</p>
<p>That same debugging instinct carried into a proper terminal deep-dive later in the week. I went through file navigation fundamentals (<code>pwd</code>, <code>ls -a</code>, <code>cd</code>, and the difference between <code>find</code>'s live search versus <code>locate</code>'s much faster indexed search), then built my first custom shell command — a <code>rename</code> function in <code>.bashrc</code> that prompts for a filename instead of typing out full <code>mv</code> syntax — and extended the same pattern into <code>copy</code> and <code>move</code> functions, checking for command-name collisions first with <code>which</code>. Getting there meant hitting three real bugs in one sitting: a syntax error from missing semicolons, arrow keys inserting garbage characters into filenames (fixed by adding <code>read -e</code> for proper line-editing), and <code>~</code> failing to expand inside a <code>read</code> prompt, since it only auto-expands as a typed command argument, not inside a variable read — fixed by manually substituting <code>$HOME</code>. None of this required knowing bash going in. The actual transferable skill was the debugging loop itself, and I compiled the whole thing into a running personal cheat sheet so it doesn't have to be re-learned from scratch.</p>
<p>Those same shell functions became the subject of my first full Git lifecycle a day later. I created a new <code>dotfiles</code> repository, cloned it into Kali, set up my Git identity for the first time, and added the bash functions in as a tracked file. Learned the three-stage workflow properly — <code>add</code> to stage, <code>commit</code> to checkpoint locally, <code>push</code> to upload — and hit a real wall almost immediately when GitHub rejected plain password authentication. Generating a Personal Access Token and using it in place of a password fixed it, which was less a coding problem and more a "how does GitHub's permission model actually work" gap. I also caught and fixed a missing closing bracket in the function code myself before committing, using pattern recognition from the earlier bash debugging session — and rewrote the README from a personal-narrative first draft into plain technical documentation, since that's what an actual reader of the code needs, not a story about my day. The repo itself is still thin — one file, three small functions, no license or <code>.gitignore</code> yet — but the workflow itself (create, clone, commit, authenticate, push, iterate) is now a known quantity instead of a mystery.</p>
<p>On the pure networking side, the standout session was DNS security — specifically TCP 53 versus UDP 53, zone transfers, DNS tunneling, and reverse DNS. DNS defaults to UDP for standard queries and falls back to TCP when responses exceed 512 bytes, during zone transfers, or for large record sets, which means TCP 53 showing up on a scan is worth a second look. Zone transfers are only meant to sync a primary DNS server to its secondaries, but misconfigured servers will hand the entire internal zone — subdomains, internal IPs, mail servers, staging environments — to anyone who asks with <code>dig axfr @nameserver target.com</code>. I tested this against a real target and got refused, which is the correct, secure outcome, not a failed command — and I used <code>zonetransfer.me</code>, an intentionally vulnerable practice domain, to see what a successful transfer actually looks like instead of testing against something I shouldn't. DNS tunneling was the other half worth remembering: attackers exploit the fact that firewalls almost always allow DNS traffic out, encoding data into subdomain queries sent to an attacker-controlled server — TCP 53 gets favored for this since it handles larger payloads and stable sessions, which is exactly how tools like <code>dnscat2</code> work, and it's a genuine SOC blind spot since most monitoring focuses on HTTP/HTTPS instead of DNS logs. Reverse DNS rounded it out — reversing an IP's octets and appending <code>.in-addr.arpa</code> to query a PTR record, handled automatically with <code>dig -x</code>, useful for quickly identifying what an unfamiliar IP in a log actually is.</p>
<p>A separate self-test session covered Ethernet naming conventions and fiber optic fundamentals — strong sessions overall, six out of eight and six out of seven, with the misses being precision issues rather than misunderstandings. SX means short wavelength, not "small," and 10GBASE-T is 10 Gbps, with the number in the name directly stating the speed rather than implying something larger. Fiber cable layers run core → cladding → buffer coating → strengthening material → outer jacket from the center out, with the light source itself belonging to the transceiver equipment rather than being a cable layer at all.</p>
<p>The week closed with something more physical: a video-guided Packet Tracer exercise building a home network topology — PC, laptop, webcam, and a wireless router. I used the auto-select cable tool correctly for wired connections and performed a full NIC swap on two separate devices, powering off, removing the wired card, installing a WPC300N wireless card, and powering back on — then, notably, repeated the exact same swap on the second device without the video walking me through it again. That repetition without hand-holding was the actual signal, more than the video-following itself.</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>One day was a genuine zero — I wasn't at home, so nothing happened, no real story there. The day after that I was back home but still logged no cybersecurity progress, though I did put real time into math, revising old material and working through Taylor's series. Not a wasted day overall, just not one that moved the security or networking track forward, and worth being honest that the streak of technical wins had exactly one full gap in the middle of it.</p>
<h2>Focus for Next Week</h2>
<p>Confirm the Tokyo Night terminal theme actually renders correctly after moving the color scheme file to its proper system path, then layer Powerlevel10k on top once that's settled. Start Phase 1 of the NDP Watcher project — reading pcap files with scapy — since the environment and Git workflow are both finally in a state where that's a realistic next step instead of another setup detour. And round out the <code>dotfiles</code> repo with an actual license and <code>.gitignore</code> so it reads as a complete, if small, project rather than a work-in-progress.</p>
]]></content:encoded></item><item><title><![CDATA[Week 6: One Enormous Monday, Then Six Quiet Days]]></title><description><![CDATA[Quick Hook / Week in Review
This week has an unusual shape: almost the entire technical output landed in a single day. Monday alone covered a real infrastructure debugging session, the actual kickoff ]]></description><link>https://zerovector.hashnode.dev/week-6-one-enormous-monday-then-six-quiet-days</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-6-one-enormous-monday-then-six-quiet-days</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Sun, 16 Aug 2026 14:33:31 GMT</pubDate><content:encoded><![CDATA[<h2>Quick Hook / Week in Review</h2>
<p>This week has an unusual shape: almost the entire technical output landed in a single day. Monday alone covered a real infrastructure debugging session, the actual kickoff of my Python learning roadmap, and a full CTI-style workflow for detecting AI-generated images. Then math obligations, a tuition day that ran long, and a couple of days out of station flattened the rest of the week down to close to nothing. Not the balance I'd want, but Monday was dense enough that it's worth walking through properly.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The day started with a genuinely annoying infrastructure problem: getting file transfer working cleanly between my host machine and my Kali VM. I landed on SCP as the actual method, with VirtualBox Shared Folders and plain drag-and-drop noted as alternatives, but getting there meant working through a real chain of errors — literal <code>&lt;&gt;</code> brackets left in a placeholder IP, unquoted spaces breaking a "Tor Browser" path, doubled quotes, and finally the actual root cause: a NAT versus Bridged Adapter networking mismatch throwing "Network is unreachable." Switching Kali's VirtualBox adapter to Bridged, pulling a fresh IP with <code>ip a</code>, and confirming the SSH service was running fixed it, and the SCP transfer from Windows PowerShell finally went through. While I was in there, I also set up shared clipboard through Guest Additions in Bidirectional mode, then went a step further and installed CopyQ for Windows-style clipboard history, since Win+V doesn't carry across the host/guest boundary by default — bound it to a hotkey and added it to autostart so it's not a one-time fix.</p>
<p>From there I moved into actually starting the Python side of things. I locked in a three-phase, twelve-project roadmap — Python fundamentals, then a Python-plus-networking bridge phase, then real cybersecurity tooling, ending in a capstone SOC lab write-up mapped to MITRE ATT&amp;CK. Decided to build all of it inside the Kali venv at <code>~/projects/python-labs</code> rather than splitting work across Windows and Linux, which should keep the environment consistent as the projects get more networking-heavy. Project 1 — FizzBuzz — got started, covering loops, modulo logic, and conditional ordering, along with the basic setup commands for activating the venv and running scripts. Even the environment hygiene was a small lesson on its own: I had to fully tear down and reset the venv while troubleshooting a broken <code>cd</code> path, and it turned out <code>projects</code> had never actually been created under <code>~</code> — it existed under <code>~/Downloads</code> instead, which is exactly the kind of assumption-checking mistake that's cheap to make and cheap to fix once you actually look.</p>
<p>The last piece of the day was building out a proper workflow for image forensics and AI-detection — something I'm treating as a CTI triage skill rather than a one-off curiosity. The pipeline runs EXIF/exiftool first, then checks C2PA credentials, then a reverse image search across Google, TinEye, and Yandex, then a manual visual artifact checklist (hands, shadows, reflections, texture), then Error Level Analysis through FotoForensics, and finally cross-checks against at least two independent AI detectors like Hive, Illuminarty, or AI or Not. Two things got reinforced hard while building this out: metadata alone is never a verdict, only a probability signal, and when detectors disagree with each other, that means "inconclusive," not "call it 50/50 and move on." The whole structure is deliberately built on intelligence-assessment logic — corroborate across independent sources before concluding anything, the same discipline CTI triage actually runs on.</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>Everything after Monday went quiet on the cybersecurity side. Tuesday and Wednesday went entirely to math — homework and studying for an upcoming test, with zero cybersecurity work either day. Thursday's tuition session ran long, and by the time I got home I was tired enough that the evening went to gaming instead of anything productive, which I'm not going to dress up as anything other than what it was. Friday and Saturday I was out of station, so those two are genuinely no-fault — there wasn't really a study session to have. Sunday I was back home, but the day went to relaxing and playing rather than even a light session, which is the one day this week I'd actually push back on myself about, since there was no real obstacle in the way.</p>
<h2>Focus for Next Week</h2>
<p>Get back into the Python roadmap and move past Project 1 — FizzBuzz was the warm-up, not the destination. Keep the image forensics workflow alive as a real project, not just a one-time build; it's got genuine portfolio and blog potential as a documented CTI-style methodology. And going into a week that's likely to have fewer travel disruptions, the goal is simple: don't let one strong day carry six quiet ones again.</p>
]]></content:encoded></item><item><title><![CDATA[Week 5: From a Dead Start to My First Full Recon Exercise]]></title><description><![CDATA[Quick Hook / Week in Review
This week nearly didn't happen. The first half was close to a write-off — backlog piling up, networking postponed for days running, the honest kind of procrastination where]]></description><link>https://zerovector.hashnode.dev/week-5-from-a-dead-start-to-my-first-full-recon-exercise</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-5-from-a-dead-start-to-my-first-full-recon-exercise</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Sun, 09 Aug 2026 16:25:08 GMT</pubDate><content:encoded><![CDATA[<h2>Quick Hook / Week in Review</h2>
<p>This week nearly didn't happen. The first half was close to a write-off — backlog piling up, networking postponed for days running, the honest kind of procrastination where you can name exactly why it's happening and still can't quite stop it. Then Thursday flipped a switch, and the back half of the week turned into the most technically dense stretch I've had yet: a brutal ports memorization session, my first taste of TryHackMe, a clean sweep on traffic types, and — the actual highlight — a full passive-and-active recon exercise on my own network that tied everything together into something that felt like real fieldwork instead of another self-test.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The turnaround started with the least glamorous topic possible: memorizing common protocol ports. I went in and only got 6 out of 16 clean on the first pass, which sounds rough until you look at <em>why</em> — every miss was a number I'd guessed wrong or forgotten, not a concept I misunderstood. SSH and SFTP share port 22 because SFTP actually runs as a subsystem inside SSH rather than being a separate service. DHCP splits into server on port 67 and client on port 68. TFTP on port 69 is for firmware, config, and PXE boot transfers — not VoIP, which is where I'd misfiled it. I had HTTP and HTTPS numbers wrong outright (80 and 443), mixed up SNMP's versions (v1/v2 are plaintext with weak auth, v3 is properly encrypted with real authentication), and needed LDAP (389) versus LDAPS (636), SMB (445), MSSQL (1433), RDP (3389), and SIP (5060 plain / 5061 over TLS) filled in. The pattern was consistent enough that it pointed to a clear fix: this needs dedicated flashcard repetition, not more conceptual review — the reasoning is already there, the raw recall isn't.</p>
<p>That same evening I tried out TryHackMe's free rooms for the first time, mostly just to see what the platform actually feels like before committing money to it. First impression: genuinely well-structured, with explanations that hold up. The plan now is to finish the networking course first, then take a focused one-month membership and get as much out of it as possible in that window rather than dragging it out.</p>
<p>The weekend is where things really came together. A VPN and IPSec session landed at 8 out of 10, with the one correction that actually mattered being that IPSec's two core protocols are AH and ESP — not AH and ISAKMP, which belongs to the separate IKE key-management layer entirely. GRE came up too, and it's worth remembering it provides zero security on its own, no encryption or even integrity hashing, which is exactly why it's so often paired with IPSec. Right after that, a traffic-types session (unicast, multicast, anycast, broadcast) went a clean 8 for 8 — full sweep, including the detail that IPv6 replaces broadcast with multicast entirely.</p>
<p>Sunday closed the week with the actual highlight: a full passive-and-active reconnaissance exercise on my own hotspot network — laptop, Kali VM, two phones, and the hotspot device itself. I ran a passive capture with <code>tcpdump -i eth0 -n -w recon_capture.pcap</code> for about five minutes to grab natural traffic, then active host discovery with <code>nmap -sn 10.234.20.0/24</code> to pull IP, MAC, and vendor info for everything live on the network. Cross-checked all of it against <code>arp -a</code> and the live ARP packets sitting in the pcap, then confirmed the gateway with <code>ip route</code>. The interesting find was a device nmap flagged as "Intel Corporate" that turned out to be my own laptop's Wi-Fi adapter, showing up separately from my Kali VM — the virtual NIC gets its own MAC and IP entirely, which I confirmed with <code>lspci</code> and <code>dmidecode</code> showing no real wireless hardware inside the VM, plus VirtualBox's known Intel-style MAC prefix for virtual adapters. Two phones showed up as "Unknown" vendor, which turned out to just be MAC randomization — a privacy feature on modern iOS and Android, not something to chase as suspicious. The real value wasn't any single finding, though — it was having three independent methods (nmap, ARP, routing table) all agree with each other, and getting to actually apply the passive-then-quiet-active-then-louder-active ordering to a real goal instead of reading about why attackers structure recon that way.</p>
<p>The same day rounded out with a Wi-Fi standards, cellular, and satellite session at 6 out of 10 first pass — again, mostly generational naming rather than misunderstood mechanics. The Wi-Fi 1/2/3 mapping was reversed in my head (it's actually b=1, a=2, g=3), and 802.11ax is Wi-Fi 6, not Wi-Fi 5. I also filled in that LTE unified two separate 3G lineages — GSM/UMTS and CDMA/EV-DO — and locked down the numbers: LTE tops out around 100 Mbps down, LTE-A theoretically around 1 Gbps, and 5G's theoretical ceiling sits near 10 Gbps (a rate, not a file size, which I'd apparently written down wrong at some point).</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>The first three days of the week were close to dead on the cybersecurity side. Monday I published the previous week's overdue report but did nothing else — no math, no self-tests, which just moved the backlog forward into a day I already knew had an HOD-led class waiting, meaning I needed to revise old material on top of everything else. Tuesday and Wednesday kept the same shape: networking kept getting postponed, and I noticed it happening in real time without managing to stop it. I don't think there's a clean external reason for that stretch — it was just low energy and momentum that hadn't built up yet, and naming it honestly here felt more useful than inventing a cause that wasn't really there.</p>
<h2>Focus for Next Week</h2>
<p>Turn the ports weak spot into an actual flashcard routine — Anki-style, spaced repetition, treated as its own recurring task instead of something folded into general review. Keep pushing to finish the networking course inside the next two weeks, since that's the real gate before TryHackMe becomes the main focus instead of a side experiment. And carry forward whatever made Thursday through Sunday work, because whatever broke the early-week stall is worth understanding well enough to trigger on purpose next time, not just wait for it to happen again.</p>
]]></content:encoded></item><item><title><![CDATA[Mapping My Own Network: A Hands-On Recon Practical (ARP, DHCP, and a VM Plot Twist)]]></title><description><![CDATA[Introduction
I wanted to answer a simple-sounding question: how many devices are actually connected to my mobile hotspot, and what are they?
My setup was small — my laptop (running Kali in a VM), my h]]></description><link>https://zerovector.hashnode.dev/mapping-my-own-network-a-hands-on-recon-practical-arp-dhcp-and-a-vm-plot-twist</link><guid isPermaLink="true">https://zerovector.hashnode.dev/mapping-my-own-network-a-hands-on-recon-practical-arp-dhcp-and-a-vm-plot-twist</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Sun, 09 Aug 2026 15:12:39 GMT</pubDate><content:encoded><![CDATA[<h2>Introduction</h2>
<p>I wanted to answer a simple-sounding question: <em>how many devices are actually connected to my mobile hotspot, and what are they?</em></p>
<p>My setup was small — my laptop (running Kali in a VM), my hotspot phone acting as the router, and two other phones connected to the same network. Simple enough to count on one hand, right? I thought so too. Turns out, actually <em>proving</em> it — with evidence, not assumptions — taught me more about ARP, DHCP, and virtualization than I expected from what I thought would be a quick 20-minute exercise.</p>
<p>This post walks through the full recon process I used, structured the way an attacker doing reconnaissance would approach it: passive first, active only when needed, and always cross-checking one source against another before trusting it.</p>
<hr />
<h2>Prerequisites</h2>
<p>To follow along, it helps to already know:</p>
<ul>
<li><p>Basic IP addressing (what an IP address and subnet look like)</p>
</li>
<li><p>What a MAC address is, at a surface level</p>
</li>
<li><p>Comfort opening a terminal and running basic Linux commands</p>
</li>
<li><p>Wireshark installed, and a Kali (or any Linux) environment with <code>nmap</code> and <code>tcpdump</code> available</p>
</li>
</ul>
<hr />
<h2>The Core Concept</h2>
<p>Every device on a local network needs two things to actually talk to other devices: an <strong>IP address</strong> (its logical "mailing address") and a <strong>MAC address</strong> (the physical hardware address baked into its network card). Devices don't naturally announce "here's my full identity" to anyone who asks — but they <em>are</em> constantly leaking information just by functioning normally.</p>
<p>Three protocols do most of this leaking, and they became the backbone of this whole exercise:</p>
<ul>
<li><p><strong>ARP (Address Resolution Protocol)</strong> — resolves an IP to a MAC address. Think of it as shouting into a room: <em>"Whoever is at this address, tell me your badge number."</em></p>
</li>
<li><p><strong>DHCP (Dynamic Host Configuration Protocol)</strong> — how a device gets assigned an IP in the first place, like checking into a hotel and being handed a room number by the front desk.</p>
</li>
<li><p><strong>mDNS (Multicast DNS)</strong> — how devices announce human-readable names on a local network without any central server, which is why your phone shows up as "Someone's iPhone" on shared Wi-Fi.</p>
</li>
</ul>
<p>None of these require an attacker (or a curious student) to send anything unusual — you just have to <em>listen</em>.</p>
<hr />
<h2>How It Works</h2>
<p>I followed a deliberate order, mimicking how a real attacker minimizes their footprint during reconnaissance — a concept that maps directly onto MITRE ATT&amp;CK's Reconnaissance and Discovery tactics:</p>
<ol>
<li><p><strong>Passive listening first.</strong> Capture traffic without sending anything. Let devices reveal themselves through normal background chatter (ARP refreshes, mDNS announcements, DHCP renewals).</p>
</li>
<li><p><strong>Quiet active scanning next</strong>, only if passive listening leaves gaps. ARP-based host discovery blends into normal network noise since ARP is required for basic connectivity anyway.</p>
</li>
<li><p><strong>Escalate only if necessary.</strong> Louder techniques (full port scans, service enumeration) generate detectable footprints and were never needed for this exercise, since the goal was just device discovery.</p>
</li>
<li><p><strong>Cross-verify everything.</strong> Never trust a single tool's output — confirm it against at least one independent source.</p>
</li>
</ol>
<hr />
<h2>Syntax / Commands / Code</h2>
<p><strong>Step 1 — Passive capture:</strong></p>
<pre><code class="language-bash">sudo tcpdump -i eth0 -n -w recon_capture.pcap
</code></pre>
<ul>
<li><p><code>-i eth0</code> — capture on this specific interface</p>
</li>
<li><p><code>-n</code> — skip DNS/port name resolution (faster, and avoids generating extra DNS traffic that would pollute the very network I was trying to quietly observe)</p>
</li>
<li><p><code>-w recon_capture.pcap</code> — write raw output to a file for later analysis in Wireshark, rather than just scrolling text</p>
</li>
</ul>
<p><strong>Step 2 — Active ARP-based sweep:</strong></p>
<pre><code class="language-bash">sudo nmap -sn 10.234.20.0/24
</code></pre>
<ul>
<li><code>-sn</code> — ping/ARP sweep only, no port scanning. This finds live hosts fast and quietly, and automatically resolves each MAC address's manufacturer using nmap's built-in vendor database.</li>
</ul>
<p><strong>Step 3 — Cross-checks:</strong></p>
<pre><code class="language-bash">arp -a          # Quick local ARP cache check
ip a            # Confirm my own machine's interface, IP, and MAC
ip route        # Confirm the actual default gateway
</code></pre>
<p>I also opened the <code>.pcap</code> in Wireshark and filtered specifically for the "free information" packet types:</p>
<pre><code class="language-plaintext">arp or mdns or dhcp
</code></pre>
<hr />
<h2>Practical Example</h2>
<p>Running the sweep gave me a full list of live hosts in one shot:</p>
<pre><code class="language-plaintext">Nmap scan report for 10.234.20.28
MAC Address: 8C:E9:EE:86:01:32 (Intel Corporate)

Nmap scan report for 10.234.20.51
MAC Address: E8:5A:8B:8C:25:B5 (Xiaomi Communications)

Nmap scan report for 10.234.20.126
MAC Address: 3E:98:EB:7C:10:31 (Unknown)

Nmap scan report for 10.234.20.138
MAC Address: 8E:05:CF:B2:E6:45 (Unknown)

Nmap scan report for 10.234.20.192
Host is up.
</code></pre>
<p>Five hosts, no MAC shown for <code>.192</code> since that was my own scanning machine. Straightforward — or so I thought.</p>
<hr />
<h2>Common Mistakes (and Where I Actually Got Stuck)</h2>
<p>This is the part I want to spend real time on, because the "clean" writeup above hides how messy this actually was to work through live.</p>
<p><strong>Mistake 1 — Trusting the vendor label at face value.</strong> <code>.28</code> showed up as "Intel Corporate." I run an AMD laptop. My first instinct was: <em>is this a rogue device? Another laptop I don't know about?</em> That's a dangerous assumption to run with unverified — nearly wrote it off as "some Intel PC on the network" before stopping to actually question it.</p>
<p><strong>Mistake 2 — Confusing CPU vendor with network chipset vendor.</strong> Even after doubting the "rogue device" theory, I initially forgot that a laptop's CPU (AMD) and its Wi-Fi <em>card</em> are completely separate pieces of hardware — plenty of AMD machines ship with Intel-made wireless chips. This cost me a detour running <code>lspci | grep -i wireless</code>, which returned nothing at all.</p>
<p><strong>Mistake 3 — Not accounting for virtualization.</strong> The empty <code>lspci</code> output was actually the real clue, and I almost brushed past it. Once I checked <code>dmidecode -s system-product-name</code> and confirmed I was inside a VM, everything clicked: my Kali instance only sees a <em>virtual</em> network adapter, not my laptop's real physical Wi-Fi card. That explained three separate confusions at once — why I had <code>eth0</code> instead of <code>wlan0</code>, why <code>lspci</code> showed nothing wireless, and why <code>.28</code> carried an Intel-style MAC (VirtualBox's virtual NICs default to Intel-like vendor prefixes).</p>
<p><strong>Mistake 4 — Assuming "Unknown" vendor meant something was wrong.</strong> Two phones (<code>.126</code> and <code>.138</code>) showed "Unknown" instead of a real manufacturer name. My gut reaction was that nmap had failed to identify them. It hadn't — this is <strong>MAC address randomization</strong>, a deliberate privacy feature on modern iOS/Android where a device generates a fake, temporary MAC per network specifically to prevent tracking. "Unknown" here is actually a <em>good</em> sign — it means the phone's privacy protections are working as intended, not a gap in my tooling.</p>
<p><strong>Mistake 5 — Misreading a DHCP packet direction.</strong> I found a DHCP Request going from my Kali VM directly to <code>.138</code>, and assumed I'd misidentified which device was the gateway — because I'd been treating <code>.138</code> as "just another phone" up to that point. Running <code>ip route</code> settled it immediately: <code>.138</code> was the actual DHCP server / default gateway (the hotspot phone) all along. The packet made perfect sense once I had the right mental model of who was who.</p>
<hr />
<h2>The "Aha" Moment</h2>
<p>Genuinely, the moment <code>ip route</code> printed <code>default via 10.234.20.138</code> was the most satisfying part of this whole exercise. Every earlier thread — the Intel mislabeling, the missing <code>wlan0</code>, the empty <code>lspci</code>, the DHCP packet aimed at a device I'd wrongly assumed was "just a phone" — collapsed into one consistent, fully explained picture within about thirty seconds of reading that one line.</p>
<p>It's a specific kind of relief that's hard to describe if you haven't felt it: the feeling of having four separate loose threads in your head, each one slightly annoying on its own, and then watching them all tie into a single, obvious knot at once. Nothing about the network had actually changed — I just finally had the right frame to interpret what I was already looking at. That's a genuinely different feeling than just "getting the right answer" from a tutorial; this was earned through actually being wrong first.</p>
<hr />
<h2>Best Practices / Tips</h2>
<ul>
<li><p><strong>Never trust a single tool's output in isolation.</strong> Cross-check nmap against ARP cache, live packet captures, and the routing table before treating anything as confirmed.</p>
</li>
<li><p><strong>Know your own hardware baseline</strong> before investigating unknown devices — I couldn't have caught the Intel discrepancy without already knowing I run AMD.</p>
</li>
<li><p><strong>"Unknown" vendor isn't automatically suspicious.</strong> Learn to recognize MAC randomization as expected, privacy-driven behavior on modern phones.</p>
</li>
<li><p><strong>Virtualization changes your network footprint.</strong> A single physical machine can appear as multiple distinct network entities (host + VM), each with independent IPs and MACs — factor this in before concluding a device is unidentified.</p>
</li>
<li><p>Always confirm the gateway with <code>ip route</code> early — it resolves a lot of ambiguity about device roles before you go chasing false leads.</p>
</li>
</ul>
<hr />
<h2>Real World Applications</h2>
<p>This exact workflow — passive listening, quiet active discovery, cross-verification, and healthy skepticism toward tool output — is directly how SOC analysts and threat hunters build an <strong>asset inventory</strong> on unfamiliar or newly-monitored networks. Recognizing VM-originated traffic, randomized MACs, and gateway identification are all everyday tasks in real network investigations, not just classroom exercises. Understanding both sides — how an attacker performs low-friction recon, and how a defender interprets the same traffic — is core to CTI and SOC work alike.</p>
<hr />
<h2>Key Takeaways</h2>
<ul>
<li><p>ARP, DHCP, and mDNS traffic passively reveal most of a network's device map without sending a single scan</p>
</li>
<li><p><code>nmap -sn</code> gives a fast, low-noise active sweep with automatic vendor identification</p>
</li>
<li><p>Vendor/OUI labels are a clue, not proof — virtualization, chipset suppliers, and MAC randomization can all mislead a surface-level reading</p>
</li>
<li><p>Cross-referencing multiple independent sources (nmap, ARP cache, routing table, live capture) is what actually builds confidence in a finding</p>
</li>
<li><p>Getting confused and working back out of it taught me more than if everything had matched cleanly on the first try</p>
</li>
</ul>
<hr />
]]></content:encoded></item><item><title><![CDATA[Week 4: The Week Theory Finally Became Hands-On]]></title><description><![CDATA[Quick Hook / Week in Review
This week didn't open well — I was still catching up on a report I'd missed the Sunday before, and even the makeup attempt got derailed when I ran into Claude's daily limit]]></description><link>https://zerovector.hashnode.dev/week-4-the-week-theory-finally-became-hands-on</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-4-the-week-theory-finally-became-hands-on</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Tue, 04 Aug 2026 15:02:55 GMT</pubDate><enclosure url="https://cdn.hashnode.com/uploads/covers/6a3d657c24201e4da544f2ec/dfde12b5-e51a-43dc-a951-86c8cc0755e3.jpg" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2>Quick Hook / Week in Review</h2>
<p>This week didn't open well — I was still catching up on a report I'd missed the Sunday before, and even the makeup attempt got derailed when I ran into Claude's daily limit mid-write. That set the tone for a week that stayed uneven right through to the end. But buried in the middle of it was a genuine turning point: my first real Wireshark session, where networking stopped being something I read about and became something I actually watched happen, packet by packet. That one session did more for my understanding than several weeks of note-taking had.</p>
<h2>Core Technical &amp; Personal Insights</h2>
<p>The technical highlight of the week was hands-on, not theoretical. I ran my first real Wireshark capture, filtering for ICMP and ICMPv6 traffic while pinging and browsing so I could see actual packets instead of just reading about them. That's where I learned ICMPv6 isn't just "ping for IPv6" — it's absorbed jobs that IPv4 splits across separate protocols, specifically ARP's job through Neighbor Discovery Protocol (Neighbor Solicitation/Advertisement) and router discovery through Router Solicitation/Advertisement tied to SLAAC.</p>
<p>The moment that actually stuck was catching a real Neighbor Solicitation → Neighbor Advertisement exchange on my own network and decoding it by hand — Ethernet header, then IPv6 header, then the ICMPv6 payload, byte by byte. Pulling out the source/destination MAC and IPv6 addresses, identifying ICMPv6 type 136 as a Neighbor Advertisement, and reading the flags byte (<code>c0</code>, Router + Solicited flags set) directly from a raw hex dump was a different kind of understanding than anything I'd gotten from slides. Along the way I learned a real detection rule too: NDP packets always carry a hop limit of 255 because they're only meant to travel one hop — if a packet claiming to be NDP shows up with a lower hop limit, it's crossed real routers to get there, which means it's spoofed. That's the first time I pulled a security-relevant insight straight out of a hex dump instead of reading it in someone else's writeup.</p>
<p>Even the confusion was useful. I got genuinely thrown for a bit trying to figure out why a single laptop was showing what looked like a two-device conversation — turned out to be my VM host or another local interface doing NDP with my own machine. Chasing that down instead of just accepting the capture at face value was its own small lesson in not trusting assumptions. Same with Wireshark's UI itself: right-click-and-copy for filtering turned out to be fragile, and I had to learn the real way — using actual field names like <code>icmpv6.type</code> and <code>ipv6.src</code> — instead of leaning on GUI shortcuts.</p>
<p>The rest of the week's technical work came from self-tests, and the pattern held up well. A cloud service models session (SaaS/PaaS/IaaS, shared responsibility, deployment models) landed at 6/8, with the only real gaps being naming precision — IaaS is also called HaaS (Hardware as a Service), and PaaS examples are things like Heroku, Google App Engine, or Azure App Service, not Salesforce, which is SaaS. A TCP/IP fundamentals session went even better at 7/8 — solid on the encapsulation analogy (IP as the truck, TCP/UDP as the boxes, the network as the road), TCP's acknowledgment-based reliability versus UDP's lack of it, and why port numbers alone were never a security measure. The two misses were just memorized numbers I'd guessed instead of recalled — the non-ephemeral port range is 0–1023, not starting at 1, email runs on port 143 not 233, and the ephemeral range is 1024–65535, not roughly 2034. Good sign either way: both weak spots were numbers to memorize, not concepts I'd misunderstood.</p>
<h2>What Didn't Go to Plan (Lessons Learned)</h2>
<p>The week started with fallout from the previous one — I still owed a report from that Sunday, and the makeup session ran into Claude's daily usage limit mid-write after a long, high-effort prompt, pushing the delay out by another day. A hectic day full of regular classes and a hangout plan, plus a genuinely long commute from home to college, left me too tired to touch networking at all — and I know it's now been several days without meaningful forward progress on the course, which needs to change before August 16th. Even a lighter day where I only managed five math questions and a single networking video came without the follow-up notes or self-test that were supposed to go with it. And on a day with real math output — nearly 31 questions — I have to be honest that a chunk of it was copying the solution method rather than working it out cold, which isn't the standard I actually want to hold myself to, even under a Thursday tuition deadline.</p>
<h2>Focus for Next Week</h2>
<p>Get back to the Wireshark-style hands-on approach more deliberately — it's already proven it teaches faster than passive note-taking, so it shouldn't stay a one-off. Close the gap on the outstanding networking video (finish the notes and self-test I skipped), and treat August 16th as a real deadline for the course, not a soft target. And on the math side: fewer "check the solution first" sessions, even if it's slower — the whole point is being able to do it cold when it counts.</p>
]]></content:encoded></item><item><title><![CDATA[Week 3: Two Good Self-Tests, One Surprise Exam, and a Report That's Late Again]]></title><description><![CDATA[TL;DR
Started strong — finally published the previous week's overdue report and scored 6/8 on a networking self-test the same day. Kept the momentum for two more sessions, catching a genuine misconcep]]></description><link>https://zerovector.hashnode.dev/week-3-two-good-self-tests-one-surprise-exam-and-a-report-that-s-late-again</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-3-two-good-self-tests-one-surprise-exam-and-a-report-that-s-late-again</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Tue, 28 Jul 2026 17:04:15 GMT</pubDate><content:encoded><![CDATA[<h2>TL;DR</h2>
<p>Started strong — finally published the previous week's overdue report and scored 6/8 on a networking self-test the same day. Kept the momentum for two more sessions, catching a genuine misconception on VPC endpoints along the way. Then a surprise math test hijacked a full day, an AI rate-limit killed another, and a big note-taking push got cut short by a power cut. By the time this report was due, nothing was left in the tank, and it's going out late. Again. Same mistake as last time, and I noticed it happening.</p>
<hr />
<h2>The week that started strong</h2>
<p>I opened the week by clearing a debt — the previous week's report finally went out, later than planned but out. Same day, I ran a self-test on IDS versus IPS, load balancers, NAS versus SAN, and proxy mechanics, and landed 6 out of 8 on the first pass. Two things needed tightening: an L3 switch isn't just "a switch with routing bolted on" — it routes between VLANs and subnets using IP, in hardware, at wire speed, which is a very different claim than the vague version in my head. And an access point bridges 802.11 into 802.3, not 802.2 — that's the LLC sublayer, a completely different layer of the stack I'd been quietly conflating. Two lecture videos got finished on top of that. A genuinely solid start, and I'm allowed to say that without immediately talking myself out of it.</p>
<h2>The self-tests kept holding up</h2>
<p>The next session went almost as well — another 6 out of 8, this time on DNS TTL, QoS naming, VPN concentrators, and routing loops. One correction actually mattered: I had the DNS TTL logic backwards. Before an IP change, you lower the TTL <em>in advance,</em> so the old, cached record expires fast, and everyone converges on the new IP sooner — I'd been picturing the whole mechanism running in the opposite direction. QoS terminology got cleaned up too; the real names are traffic shaping or traffic/bandwidth prioritization, not "packet shaping," which I'd apparently invented with total confidence.</p>
<p>A cloud networking self-test followed — 5 out of 8, three fixes needed, and one of them wasn't just sloppy wording. I genuinely had VPC endpoints wrong: they connect privately to the <em>same</em> cloud provider's own services, not a bridge between two different providers' VPCs like I'd assumed. Internet Gateways got a smaller correction too — they handle traffic both ways for public-IP resources, not just inbound. That one landed at 9:45 PM, cutting it close, but it still counts.</p>
<h2>Then math ambushed me</h2>
<p>One full day disappeared without a single minute going to networking. The head of the mathematics department sprang a surprise check on Class 11 and 12 basics, and I spent the entire day frantically re-learning material I hadn't touched in two years, purely so I wouldn't embarrass myself in front of an actual department head. My first math tuition class landed the same day — went fine, got practice questions, and discovered mid-session that I need an actual dedicated notebook before I can be consistent about any of it. Apparently, stationery is a prerequisite for discipline, which nobody warns you about but still no solution in sight sadly.</p>
<h2>The AI token apocalypse</h2>
<p>I tried to recover the next stretch by writing notes for three more lecture videos, and I did — but it took long enough, and burned through enough tokens, that I got rate-limited mid-session and had to stop entirely. No other study happened that day, college or cybersecurity. Losing a day because your own note-taking tool ran out of gas is a very specific, very 2026 way to fail at being productive.</p>
<h2>The marathon, then the blackout</h2>
<p>I came back hard after that — eleven straight videos of notes in one sitting, a real push. Then the power went out. Repeatedly. The session ended there, and math homework didn't get touched either. Still, eleven videos of notes in one day is not nothing, and I'm keeping that win without an asterisk attached to it.</p>
<h2>Where it fell apart again</h2>
<p>By the time this report was due, I had nothing left — tuition homework got done, nothing else did. No further networking notes, no further study. And the report itself went out late, same as last time, exactly one cycle apart. That's not bad luck twice. That's a pattern I need to actually name instead of quietly noting and moving on from.</p>
<h2>The numbers</h2>
<ul>
<li><p>3 self-tests: 6/8, 6/8, 5/8</p>
</li>
<li><p>Roughly 13 lecture videos noted across the week</p>
</li>
<li><p>1 genuine misconception caught and corrected (VPC endpoints)</p>
</li>
<li><p>1 surprise exam survived without public humiliation</p>
</li>
<li><p>2 days with zero networking progress</p>
</li>
<li><p>2 late weekly reports in a row</p>
</li>
</ul>
<h2>Going into Week 4</h2>
<p>Same fix I keep writing down and not fully honoring: one fixed daily block, protected, no exceptions for surprise tests or dying AI tokens. And the report gets a hard deadline this time, not a "sometime around Sunday" one — if it's late again next week, that's the actual headline, not something buried at the bottom.</p>
]]></content:encoded></item><item><title><![CDATA[I Procrastinated the Post About Not Procrastinating (Week 2) ]]></title><description><![CDATA[TL; DR: 5 working days, 2 zero days. Real wins: finished Bandit level 1 and started documenting it, finally understood the epsilon-delta limit definition after fighting it, found a full self-study roa]]></description><link>https://zerovector.hashnode.dev/i-procrastinated-the-post-about-not-procrastinating-week-2</link><guid isPermaLink="true">https://zerovector.hashnode.dev/i-procrastinated-the-post-about-not-procrastinating-week-2</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Mon, 20 Jul 2026 07:35:54 GMT</pubDate><enclosure url="https://cdn.hashnode.com/uploads/covers/6a3d657c24201e4da544f2ec/063e42c3-b909-4a54-adaf-3fdbfce0ae8c.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><strong>TL; DR:</strong> 5 working days, 2 zero days. Real wins: finished Bandit level 1 and started documenting it, finally understood the epsilon-delta limit definition after fighting it, found a full self-study roadmap (networking → Linux → Wireshark) via a GitHub repo and Professor Messer's Network+ playlist, and scored 4/5 on a first self-test on the OSI model. Also: Hashnode auto-removed last week's post and I had to appeal it, which ate a night I'd planned to use for writing. And yes — this exact post about weekly consistency was itself a day late. I noticed. Let's get into it.</p>
<hr />
<p>Day one of the week, I did nothing. Not "low output" — nothing. Just a flat zero to open on, which is not the start you want when the entire point of this blog is proving I can hold a system together outside a classroom.</p>
<p>Then something clicked on day two, and the rest of the week turned into this uneven back-and-forth between actually working and actually not — which, if I'm honest, is a more accurate picture of my process than a clean streak would've been.</p>
<h2>The days that worked</h2>
<p>Day two was the real start: read through the syllabus, got a working sense of the first unit, and roughly sketched a system for two things — learning technical material, and turning it into blog posts worth reading. Bandit was on the list for that day too. It didn't happen. Filed under "tomorrow," which by now I know is a phrase that needs watching. It is dangerous, trust me.</p>
<p>Day three delivered on it. First real class for both Math and CS, and I went in swinging on the epsilon-delta definition of limits — the kind of definition that reads like nonsense until one explanation flips a switch and suddenly it's obvious. Video did the flipping. Also cleared Bandit's first level and started writing it up properly instead of just moving on. Not a huge technical leap, but a real one — <strong>the difference between doing something and doing something <em>documented</em>.</strong> Even though I know it I still get caught in that.</p>
<p>Day five is where the actual roadmap took shape. Found a GitHub repo built specifically for starting in cybersecurity — playlists, structured materials, an actual path instead of a pile of links. Decided on the order: <strong>networking first, via Professor Messer's Network+ playlist, then Linux, then Wireshark once the protocol theory has somewhere to land.</strong> That sequencing matters more than it sounds — Wireshark before you understand ports and protocols is just staring at scrolling noise.</p>
<p>Day six, math pulled its weight — tangent and normal, some solid problem sets, a small group study session that covered both that and a recap of limits and derivatives. But cybersecurity got zero that day. No second network video, no OSI revision. Split attention, one side winning.</p>
<p>Day seven: cleared the backlog of pending math work — took longer than expected — and got through three more Professor Messer lectures, notes and all. Also the day this report was originally due. It wasn't written. Filed under "tomorrow" again, and this time I actually noticed the pattern repeating in real time, which is either progress or just a more self-aware way of doing the same thing.</p>
<h2>The one deliverable I'm actually proud of</h2>
<p>Buried in day six is a self-test on OSI layer fundamentals — five questions, first pass, no notes open. Worth showing the actual work instead of just claiming it happened:</p>
<p><strong>Q1 — A cable just won't connect. Which layer, and why?</strong> Layer 1, Physical. Cabling, connectors, signal transmission — that's the whole job of this layer.</p>
<p><strong>Q2 — Which layer routes traffic using IP addresses?</strong> Layer 3, Network. First-pass answer said Layer 5 — Session — which isn't even in the right neighborhood. Routing by IP address is Layer 3's entire reason for existing.</p>
<p><strong>Q3 — The two dominant Layer 4 protocols, and the real difference?</strong> TCP and UDP. TCP is connection-oriented and reliable — acknowledgments, retransmission, guaranteed order, at the cost of speed. UDP skips all of that for speed, which is why it's the one under streaming, DNS, and gaming.</p>
<p><strong>Q4 — Where does TLS encryption technically live in the OSI model?</strong> Layer 6, Presentation — the textbook answer, since that layer owns encryption, compression, and formatting. Worth flagging for later: in actual TCP/IP terms, TLS sits functionally between Transport and Application. The OSI mapping is the simplified version, but it's the one that shows up on exams.</p>
<p><strong>Q5 — A switch is misforwarding traffic. Whose problem is that?</strong> Layer 2, Data Link. Switches forward based on MAC addresses, so misforwarding traces back to MAC tables, VLAN config, or switching logic.</p>
<p>4 out of 5 clean, one real mistake caught and fixed. That's a better week-one signal than a perfect score would've been — a perfect score wouldn't have told me anything about where the gap actually is.</p>
<h2>The subplot nobody asked for</h2>
<p>Sometime on day three I found out Hashnode had pulled my previous post — automated removal, no warning. Wrote an appeal email that night, which took longer than expected and used up the exact hours I'd planned for the report. Still waiting to hear back. Not blaming the platform for the rest of the week's gaps, but it's a real example of how one unplanned fire can quietly eat the thing you actually meant to do.</p>
<h2>The part I'm not going to dress up</h2>
<p>This report was due on day seven. It's going out a day late. I'm writing a weekly post about staying consistent, and the post itself missed its own deadline — which is either the least surprising sentence I've written all week, or the most honest one. Possibly both.</p>
<h2>Going into week 3</h2>
<p>Same fix as planned, said with more conviction now that I've watched it fail once already: one fixed time block, same time every day, protected before anything else gets scheduled into it. Not "whenever there's energy" — a slot on the clock, checkable by anyone reading this.</p>
<p>The report itself gets a hard deadline too, not a soft "Sunday-ish." If it's late again next week, that's the headline, not a footnote.</p>
]]></content:encoded></item><item><title><![CDATA[Week 1: Well, That Didn't Go As Planned]]></title><description><![CDATA[So, this was supposed to be the first weekly writeup of my whole system — daily journaling, Saturday CTF grind, Sunday synthesis into a post. Instead, I'm sitting here on the last day of the week tryi]]></description><link>https://zerovector.hashnode.dev/week-1-well-that-didn-t-go-as-planned</link><guid isPermaLink="true">https://zerovector.hashnode.dev/week-1-well-that-didn-t-go-as-planned</guid><dc:creator><![CDATA[Bibhor Dutta]]></dc:creator><pubDate>Sun, 12 Jul 2026 16:06:56 GMT</pubDate><content:encoded><![CDATA[<p>So, this was supposed to be the first weekly writeup of my whole system — daily journaling, Saturday CTF grind, Sunday synthesis into a post. Instead, I'm sitting here on the last day of the week trying to figure out what to even say, because the honest answer is: not much happened.</p>
<p>Let me just walk through it instead of dressing it up.</p>
<h2>The part that stings a bit</h2>
<p>Most of the week, I did basically nothing on the security side. No TryHackMe, no Bandit, no structured study. College started, and the first day I came home genuinely wiped out — that one I don't feel bad about, that's just real life. But instead of resetting the next day, I let that tiredness become an excuse, and one off day turned into several. Games and random videos ate the time that was supposed to go into learning.</p>
<p>And the part that actually bugs me more than the missed work itself — I had built a fallback for exactly this situation. "Even on a bad day, do the 15-minute version, keep the chain alive." I didn't even do that. I just... skipped it. Not because the fallback was too hard, but because once you miss one day it gets weirdly easy to justify missing the next.</p>
<p>So yeah. No sugarcoating — this week was mostly games and videos where study was supposed to be.</p>
<h2>What actually did happen, though</h2>
<p>It wasn't a total zero, even if it feels that way:</p>
<ul>
<li><p>Sorted out an annoying setup issue with the new Obsidian vault</p>
</li>
<li><p>Actually wrote proper notes for the first couple of days</p>
</li>
<li><p>Found a free platform + certificate route worth checking out before spending money on TryHackMe, plus did a little digging into how it's structured</p>
</li>
<li><p>Sat down and read through the <strong>entire semester-wise curriculum PDF</strong> — genuinely useful, now I know what's coming in every semester, especially this one:</p>
<ul>
<li><p>Major-1: Computer Fundamentals and Digital Logic</p>
</li>
<li><p>Major-2: Introduction to Programming using C</p>
</li>
<li><p>Minor-3: Introduction to Programming using Python</p>
</li>
<li><p>Minor-4: Data Structures &amp; Algorithms</p>
</li>
<li><p>Minor-6: Operating Systems</p>
</li>
</ul>
</li>
</ul>
<p>That curriculum read-through matters more than it sounds like on paper — I'm not walking into class blind now, I know roughly what to pre-read before each subject actually starts.</p>
<h2>What I'm taking from this</h2>
<p>I already know my own pattern — big ambition, then a discipline dip, then feeling bad about it, then repeat. This week is basically that pattern on display in real time. Knowing that about myself doesn't make it not happen, apparently. But at least I'd rather write it down honestly than pretend week 1 went fine when it didn't.</p>
<h2>Going into week 2</h2>
<p>Not going to list five fixes, because that's usually how I set myself up to fail again. Just one thing: <strong>a fixed time block, same time every day, even if it's only 20–30 minutes.</strong> "Study more when I get the energy" isn't a plan, it's just hoping. A fixed slot is something I can actually check myself against.</p>
<p>I'm also cutting one goal off my original list for this next cycle — better to actually hit a smaller target than keep missing a bigger one.</p>
<p>Next Sunday's post will say straight up whether that time block actually held or not.</p>
]]></content:encoded></item></channel></rss>