<?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" xmlns:media="http://search.yahoo.com/mrss/"><channel><title><![CDATA[pstree]]></title><description><![CDATA[Thoughts─└─{Ideas}└─{Stories}]]></description><link>https://pstree.cc/</link><image><url>https://pstree.cc/favicon.png</url><title>pstree</title><link>https://pstree.cc/</link></image><generator>Ghost 5.50</generator><lastBuildDate>Mon, 06 Apr 2026 11:00:19 GMT</lastBuildDate><atom:link href="https://pstree.cc/rss/" rel="self" type="application/rss+xml"/><ttl>60</ttl><item><title><![CDATA[Macros are great; ffs stop using macros.]]></title><description><![CDATA[<h2></h2><p>Macros are awesome. Macros are powerful. Macros will single-handedly turn your simple, readable codebase into an incomprehensible Lovecraftian nightmare of arcane symbols and unpredictable behavior. And yet, every day, developers continue to reach for them like a moth to a flame.</p><p>So, what&#x2019;s the deal? Why are macros</p>]]></description><link>https://pstree.cc/macros-are-great-stop-using-macros/</link><guid isPermaLink="false">677e728396636b1ca22f846e</guid><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Fri, 21 Feb 2025 12:29:55 GMT</pubDate><media:content url="https://pstree.cc/content/images/2025/02/sQlq3.png" medium="image"/><content:encoded><![CDATA[<h2></h2><img src="https://pstree.cc/content/images/2025/02/sQlq3.png" alt="Macros are great; ffs stop using macros."><p>Macros are awesome. Macros are powerful. Macros will single-handedly turn your simple, readable codebase into an incomprehensible Lovecraftian nightmare of arcane symbols and unpredictable behavior. And yet, every day, developers continue to reach for them like a moth to a flame.</p><p>So, what&#x2019;s the deal? Why are macros both a godsend and a cursed artifact? And why, for the love of all that is good and holy, should you stop using them in most cases?</p><p>You know the drill. Take a moment before scrolling down.</p><h2 id="wtf-are-macros">Wtf are macros?</h2><p>At their core, macros are a way to tell the compiler (or preprocessor, depending on the language) to replace one piece of code with another&#x2014;usually at compile time. This can mean anything from simple text replacement (<code>#define</code> in C) to full-on metaprogramming sorcery (Rust&#x2019;s procedural macros, Lisp&#x2019;s <strong><em>everything</em></strong>).</p><p>Macros can be used to:</p><ul><li>Generate repetitive boilerplate</li><li>Optimize performance by inlining code</li><li>Perform compile-time computations</li><li><em><strong>Completely wreck your debugging experience and make outages a living hell.</strong></em></li></ul><h2 id="macros-are-great-sort-of">Macros are great! (Sort of.)</h2><p>Macros exist because they solve real problems. Let&#x2019;s take an example in Rust:</p><pre><code class="language-Rust">macro_rules! make_struct {
    ($name:ident) =&gt; {
        struct $name {
            data: i32,
        }
    };
}

make_struct!(Foo);
make_struct!(Bar);</code></pre><p>Boom! We just created two structs without writing the same code twice. Feels great, right?</p><p>Or in C:</p><p><code>#define SQUARE(x) ((x) * (x))</code></p><p>Nice! We don&#x2019;t have to write a function for squaring a number. More efficient, right?</p><p>But then, some poor soul writes this:</p><p><code>int result = SQUARE(5 + 2);</code></p><p>And the compiler happily expands it to:</p><p><code>int result = (5 + 2 * 5 + 2);</code></p><p>Which evaluates to <code>14</code>, not <code>49</code>. Congratulations, you have just entered <em>Macro Hell&#x2122;.</em></p><h2 id="the-dark-side-of-macros">The dark side of macros</h2><p>While macros give you power, they come with some very nasty trade-offs:</p><h3 id="1-debugging-macros-is-pain-incarnate">1. <strong>Debugging macros is pain incarnate</strong></h3><p>Ever tried stepping through a macro in a debugger? It&#x2019;s like trying to read a book that&#x2019;s being rewritten while you turn the pages. Since macros operate before actual compilation, they don&#x2019;t exist in your final code in a way that debuggers can follow.</p><h3 id="2-macros-break-syntax-highlighting-and-tooling">2. <strong>Macros break syntax highlighting and tooling</strong></h3><p>A good IDE can handle functions, classes, and modules. But when you start using macros, all bets are off. Code completion stops working, error messages become cryptic, and syntax highlighting goes on strike.</p><h3 id="3-macros-introduce-hidden-complexity">3. <strong>Macros introduce hidden complexity</strong></h3><p>What looks like a single macro call could expand into a monstrous web of conditional branches and recursive templates. Your future self (or your teammates) will curse you when they have to decipher the spaghetti code generated by an innocent-looking macro.</p><h3 id="4-better-alternatives-exist">4. <strong>Better alternatives exist</strong></h3><p>Most modern languages offer built-in solutions that achieve the same goals <em>without</em> the pain of macros:</p><ul><li><strong>Inline functions</strong> (C++, Rust, etc.)</li><li><strong>Generics and templates</strong> (C++, Rust)</li><li><strong>Metaprogramming tools</strong> (Python decorators, Rust&#x2019;s <code>derive</code>, etc.)</li><li><strong>Prebuilt utilities</strong> (Why write a macro when a standard library function exists?)</li></ul><h2 id="when-should-you-actually-use-macros">When should you actually use macros?</h2><p>Let&#x2019;s be fair&#x2014;there <em>are</em> cases where macros are the right tool for the job:</p><ul><li><strong>Domain-Specific Languages (DSLs):</strong> Rust&#x2019;s <code>tokio::main</code> macro, Lisp&#x2019;s everything.</li><li><strong>Compile-time computations:</strong> If your language lacks constexpr-style evaluation.</li><li><strong>When no other alternative exists:</strong> Some low-level performance-critical cases.</li></ul><p>But for everyday coding? Macros are overkill. Just use functions, generics, or templates instead.</p><h2 id="conclusion">Conclusion</h2><p>Macros are powerful, but with great power comes great unreadability. Use them <em>only</em> when necessary, and for everything else, let the compiler do the work with more maintainable alternatives.</p><p>If you must use macros, at least document them properly, or risk summoning eldritch horrors into your codebase.</p><h2 id="further-readings">Further readings</h2><ul><li>Hygienic Macros in Rust</li><li>C Preprocessor Nightmares</li><li>How Lisp Macros Work</li><li>Template Metaprogramming in C++ (A Cautionary Tale)</li></ul>]]></content:encoded></item><item><title><![CDATA[What people don't get about decentralization]]></title><description><![CDATA[<p>This post is a thought dump of a 40-hour worth of no-internet flight time I had over the last week. It was rough.</p><h2 id="intro">Intro</h2><p>This is not meant to be a linguistics lecture but more of an attempt to set a mental model for what the word decentralization in the</p>]]></description><link>https://pstree.cc/what-people-dont-get-about-decentralization/</link><guid isPermaLink="false">62a0d14ef8493f1229f7c3f0</guid><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Mon, 27 Jun 2022 14:19:02 GMT</pubDate><media:content url="https://pstree.cc/content/images/2022/06/0__y6NFTTFXekb9EP6-1.jpeg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2022/06/0__y6NFTTFXekb9EP6-1.jpeg" alt="What people don&apos;t get about decentralization"><p>This post is a thought dump of a 40-hour worth of no-internet flight time I had over the last week. It was rough.</p><h2 id="intro">Intro</h2><p>This is not meant to be a linguistics lecture but more of an attempt to set a mental model for what the word decentralization in the blockchain space can mean. You probably ran into angry tweeps claiming true decentralisation is not possible and crypto bros saying governments will be managed by DAOs in the future. But are they talking about the same thing? Can we define what decentralisation is? is it even one thing?<br>The goal from this blog is to go over some of the decentralization ethos, how they can manifest in the crypto space and what does that all mean for you.</p><h2 id="new-word-polysemy">New word: <strong>Polysemy</strong></h2><p>I was trying to find the English expression for &quot;A word that has the capacity to mean many things&quot; and it seems Polysemy is just that. In engineering capacity, I&apos;m usually very reluctant of using the words decentralized/decentralization/decentralize liberally without clarifying &quot;Decentralization of what?&quot;<br>So I guess this is a good space to go over all the ways Crypto is decentralized (and sometimes not at all).</p><p>The core definition of decentralization is the <em><strong>dispersion of power.</strong></em> It&apos;s very important to let this settle in. My view of decentralization is that it breaks down powerful singletons but it does not promise complete freedom. It follows economical consensus in decision making. Blockchains build over this concept by implementing different economical guarantees to incentivize productive behaviors and disincentivize malicious ones.</p><h2 id="decentralization-of-opportunity">Decentralization of Opportunity</h2><p>This is the most obscure term but the one I like the most. <strong><em>Decentralization of opportunity means that opportunities in markets (DeFi, creative, insurance, etc) should be fairly available across the globe.</em></strong></p><p>One of the usually debated topics about crypto is &quot;why the hype on a seemingly expensive way to do exactly the same things we used to do before?&quot; At the end of the day, you can browse the internet, watch videos, trade stocks and put your money in a bank without blockchains right?</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2022/06/5cjf4n--1-.png" class="kg-image" alt="What people don&apos;t get about decentralization" loading="lazy" width="864" height="431" srcset="https://pstree.cc/content/images/size/w600/2022/06/5cjf4n--1-.png 600w, https://pstree.cc/content/images/2022/06/5cjf4n--1-.png 864w" sizes="(min-width: 720px) 720px"><figcaption>Right?</figcaption></figure><p>For me, decentralization of opportunity is one of the biggest factors that sold me on crypto and blockchains. If there is a better alternative that offers the same decentralization of opportunity the same way crypto does, I&apos;m a buyer.<br>There are many many examples how the current financial/technology sectors are <em>NOT fair</em> and <em>walled</em> from the public. It becomes much clearer when you study how VCs behave where their portfolios are in conflict, the &quot;buy the market first&quot; by company S and it&apos;s backers or nasty deplatforming techniques by company A. It&apos;s also very apparent for anyone who spend 10 mins to study the current financial system especially on the trading arm. I want to dig deeper into both themes starting with the latter and break down how decentralization of opportunity has a huge potential.</p><h3 id="why-its-not-fair-for-you-to-trade-on-the-stock-market-today">Why it&apos;s not fair for you to trade on the stock market today?</h3><p>To place a trade as a retail investor, let&apos;s say for AMD stock, you are placing yourself under the mercy of 3-4 corporates. Let&apos;s dig deeper how this happens:</p><p>1- Alice places a trade BUY 100 AMD on broker X</p><p>2- <strong><em>Broker X</em></strong> now does two things, it gets it&apos;s slippage/spread % and trading fee (% or const) from Alice&apos;s account and match Alice from an opposing trade on it&apos;s order book (Think about it as a SELLER selling 100 AMD, but it&apos;s more complicated than that)</p><p>3- Moreover, that SELLER &#xA0;is a market maker 75-80% of the time (US market datapoint) and is the SAME market maker 35% of the time. In a traditional financial system, a market maker is a corporation that pools money from wealthy individuals, trades with very large volumes with the goal of making money by buying from sellers at price and selling again at a higher price. They benefit from much better prices, they can front run retail (most market makers are literally hardwired to exchanges so they can submit trades quicker than anyone) but they pinky promise they won&apos;t do any of that. I guess you&apos;ll have to trust them.</p><p>4- Taking it one notch up, Your broker can (<a href="https://www.washingtonpost.com/business/2021/01/29/robinhood-citadel-gamestop-reddit/?ref=pstree.cc">and boy they do</a>) share your trading data to a market maker before they execute your trade, giving them a huge advantage on the price they set for your order (and other people&apos;s)<br><br>5- On the blurry lines between what&apos;s legal and what&apos;s right, Your broker can totally <a href="https://www.forbes.com/advisor/investing/robinhood-gamestop-trading/?ref=pstree.cc">manipulate trading and halt your trades</a> if it doesn&apos;t work out for giants footing their bill.</p><p>The biggest things to notice about this paradigm is not the flagrant unfairness of this model or the strong misalignment in incentive. For the sake of our attempt to define decentralization of opportunity, the most important part in our previous model is permissions. To become a market maker you need permission from every exchange, to participate in market making you need to meet a very large wealth requirements. Market makers are very picky of whom they manage the money for. Market making is mostly restricted to regulated markets like equity and commodities but there are very very few market making companies for private equity, art, other niche investments.<br><br>To trade you&apos;ll need a permission from the broker, and you are bound by that permission that <a href="https://www.ufgwm.com/english-publications/interactive-brokers-banned-russians?ref=pstree.cc">a broker can take away anytime they feel insecure</a>.<br><br><strong>What does crypto offer (or aspires to*)?</strong></p><p>Less hops between you and services both as a consumer and as a service provider. A decentralized application allows you to use it as long as you have a wallet on the blockchain. You like it a bit too much? run a validator node, contribute in governance, stake value onto the chain.<br><br>Projecting this to DeFi, you place trades through an automated market maker where ANYONE can participate and benefit from same slippage and APY without third parties taking the larger cut. Even better, BE the market maker, be the liquidity provider to traders and benefit from the return traditional market makers are making with your 100$ bill without any approvals, min requirements, etc.</p><p><strong>Pitfall #1:</strong><br>Most crypto trading at the moment is happening on custodial exchanges. Not at all decentralized and rarely benefiting from all the previous stuff. Stuff like Celsius (the def not a bank) and CEX where you don&apos;t own your money are NOT DeFi. They have the same parasitic effect on Crypto as early Tech companies had on computing and then the internet. Trying to wrap a social endeavour into a money making machine. Celsius investment strategy is literally putting your money in DeFi protocols and making a cut on it. They are the not-so-creative middlemen of crypto. Same goes to most CEXs. </p><blockquote class="kg-blockquote-alt">Not your keys, not your money.</blockquote><h2 id="decentralization-of-initiative">Decentralization of Initiative</h2><p>Decentralization of initiative is not something new, not something crypto brings to the table. It&apos;s probably here for ages. I have the urge to define it and point it out because this is usually what people overlook when they are looking at the crypto space holistically. Blockchain efforts are not linear, people from all over the place with all different backgrounds are trying and experimenting different ideas ( &#x2200; Idea I(X, Y) s.t X &#x2208; [Brilliant, Dumb], Y &#x2208; [Succeeds, Fails] )</p><p>Outsiders usually view crypto as one pot of action. Even the most educated ones who try harder will probably have a split view of crypto and nothing more, memecoins and serious initiatives. But the thing is, crypto is way too large to abstract away as any number of teams. It has all the colors and all the types of mindsets. Crypto have the builders who succeed, builders who fail, scammers who succeed, scammers who fail, etc.</p><p></p><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2022/06/1411410a4e1717b8c0137ecc2f544a1d.jpg" class="kg-image" alt="What people don&apos;t get about decentralization" loading="lazy" width="640" height="317" srcset="https://pstree.cc/content/images/size/w600/2022/06/1411410a4e1717b8c0137ecc2f544a1d.jpg 600w, https://pstree.cc/content/images/2022/06/1411410a4e1717b8c0137ecc2f544a1d.jpg 640w"></figure><p>I love that about crypto. Crypto ethos are being implemented in a decentralized manner. Builders are opinionated and critical of other builders. Also they are very smart (<a href="https://www.reddit.com/r/ethereum/comments/tkwwr1/by_my_hand_dai_will_die_new_bizarrely_misguided/?ref=pstree.cc">Most of the time</a>). Companies building in the crypto space have VERY smart engineers and scientists working on extremely hard problems. Turing award winners are doing research on crypto, many renowned distributed systems engineers and highly cited scientists. Researchers behind Paxos, ZKP, BLS, etc are working actively on ensuring guarantees that twitter critics can do a &quot;hot take&quot; on a Twitter thread. Do your own research.<br><br>The core teams (the actual builders, both who succeeds and those who fails) are the most critical about each other. They are VERY opinionated. The founders of every L1 don&apos;t agree on most things. Most of them are genuinely trying to build something that fulfills the crypto ethos.</p><p>Most of the valid criticism coming from crypto critics is not new material. It&apos;s well known problems that crypto folks are actively working on solving. Things like MEV, Discovery, State pruning, etc are well known and actively being researched.<br><br><strong>Pitfall #2:</strong><br>Any niche new tech should be actively criticized. Especially when it&apos;s being built for public use. Crypto is it&apos;s first steps into mainstream use. The first email ever was sent in 1971. The first commercially available email came 30 years later. You probably used emails 40 years later. <strong><em>Big things take time</em></strong>. Internet was first proposed in the 1960s, after many many iterations TCP was created 1970s, adopted by DARPA for military use 10 years later and became public 25 years afterwards to only become mainstream 35 years after that. The idea that internet took 10 years to be what it&apos;s or that it&apos;s been so long for crypto is <strong>so naive.</strong> The only difference between now and then is that before, things were invented behind a curtain, they broke behind a curtain and iterated on behind the curtain. Crypto failed repeatedly, in public. You can open the tx that drained UST and read the code for the exploit that exploited Polynetwork (<em>heck, you can try the exploit yourself</em>). Early adopters always risk high volatility/bugs/vulnerabilities this is true for any kind of investment. If you expect 10x but not 0.1x, life ought to teach you otherwise.</p><h2 id="decentralization-of-governance">Decentralization of Governance</h2><p>One of the core misconceptions about crypto is that it&apos;s a software-first initiative. While the software is complex enough for software engineers to shed tears when debugging distributed systems bugs in an open source p2p software, <strong>the most important part of crypto is the social layer</strong>. &#xA0;Most dApps are open sourced contracts ANYONE can read, fork, audit, improve, out, etc. The most important reason &#xA0;ETH or BTC ever had a price (Beside on-chain value generation) is that there are at-least two people who agreed to exchange these coins at that price.</p><p><br><strong>Decentralization of Governance is the dispersion of centralized authority into a broader social consensus.</strong></p><p>It means no single person/entity should be allowed too much authority over a network. This can be defined in so many ways but there is one way that matters to me personally. People should be able to be anything, do anything on the network <strong>as long as <em>the economical consensus on the chain allow it</em></strong>. The idea that web3 is built for criminals and others is <a href="https://www.chainalysis.com/?ref=pstree.cc">painfully detached from reality</a>. A web with no governance would suck for everyone. Tor is a very practical life experiment. It had MANY great utilities. Having censorship resistant web makes it very hard on govs to censor journalism the way many countries did on the current web. Decentralization of authority make it so not one politician with too much power can BAN something on the internet just because they don&apos;t like it. Blockchains aspire* to only adhere to economical consensus. The problem with Tor is that it came with a price in the form of many dark corners. My view of Web 3.0 aspires to deliver on the censorship resistant content that only works with economical consensus mechanisms in place. If the chain&apos;s economical consensus want wikileaks, wikileaks stay. People with stake control the content.<br><br><strong>Pitfall #3:</strong><br>Borrowing from the prev section &quot;Decentralization of Initiative&quot;, Decentralization of Governance can&apos;t be maintained if you entrust a middleman like <a href="https://www.cbc.ca/news/canada/ottawa/mareva-injunction-order-extended-freedom-convoy-crypto-financial-donations-frozen-1.6366975?ref=pstree.cc#:~:text=Rare%20legal%20move%20freezes%20cash%2C%20crypto%20tied%20to%20Ottawa%20protest&amp;text=An%20Ontario%20court%20has%20frozen,in%20Canada%20to%20target%20cryptocurrency.">Centralized Exchanges or Definitely not banks like Celsius</a>. Also, due to being the youngest of the crypto family, <a href="https://www.cnbc.com/2022/06/20/users-of-defi-app-solend-block-attempt-to-take-over-whale-account.html?ref=pstree.cc">it still need some working on</a>.</p><p><strong>Pitfall #4:</strong><br>Governance v. Delegation: In a blockchain space, most of the software is obscure to non-tech people. As a non-technical person, you feel you are trusting a specific developer to deliver on their code. And that might be true but it&apos;s very different from today&apos;s model. Successful protocols have their code open-source, they are audited by the public, they are checked by every techie with stake in the matter. You are not trusting the specific developer building the protocol, you are trusting the social consensus that this is a good/bad protocol.</p><h2 id="a-glimpse-into-the-future-of-web-30">A glimpse into the future of Web 3.0</h2><p>This is purely a personal interpretation of many many conversations I had around where folks see Web 3.0 going. It&apos;s prone to change, prone to collapse or evolve. It&apos;s a speculation for that matter.</p><p>Your music is supplied on a decentralized app, they are held by their owners as NFT/Whatever-Standard-Emerges and you pay royalty to stream, you pay less for your subscription, your money goes directly to musicians publishing their music as royalties instead of paying <a href="https://www.musicbusinessworldwide.com/spotify-says-it-cant-pay-songwriters-better-royalty-rates-its-also-spending-320-million-on-a-barcelona-sponsorship-deal/?ref=pstree.cc#:~:text=In%20both%20cases%20(2018%2D2022,i.e.%20a%2030%25%20cut).">~90% to the platform.</a> % goes to stakers, those are people, some can be corporates, but mostly, people.<br><br>Your ride hailing app is decentralized, the largest portion goes to the driver, instead of <a href="https://www.uber.com/gh/en/drive/basics/tracking-your-earnings/?ref=pstree.cc#:~:text=Uber%20charges%20partners%2025%25%20fee,The%20use%20of%20Uber%20software">25% cut going to the platform</a> a much less % goes to node operators. You like a certain ride hailing app? be a node operator, be a staker. No permissions required.</p><p>Stock market is tokenized, 24 hrs. Market makers are automated. <a href="https://blog.chain.link/chainlink-fair-sequencing-services-enabling-a-provably-fair-defi-ecosystem//?ref=pstree.cc">No front running</a>, <a href="https://data.chain.link/?ref=pstree.cc">no opaque pricing</a>. Anyone can be a market maker. Microloans are instant. <a href="https://www.deco.works/?ref=pstree.cc">Mortgages are equitable and privacy-maintaining </a>. <a href="https://chain.link/use-cases/insurance?ref=pstree.cc">Insurance is parametric and provably fair</a>. <br><br>You own your data on the blockchain with a decentralized identity. No need to ask platforms to delete your data because they don&apos;t have your data. You onboard your data to the social network when you login. You allow them to write their own &quot;Directory&quot; to your data. You move your data around platforms and at will, you can delete any piece of data.. Forever.</p><p><a href="https://basicattentiontoken.org/?ref=pstree.cc">You get paid for watching ads</a>, you selectively choose to share your data with ad networks (and when to not) That money goes between you and the platform running the ad placement so they can fund your app usage. You get to choose to fund your usage with money instead of watching ads.</p><p>You use your money, both tokens and fiat, liberally. You can send money overseas for a <a href="https://l2fees.info/?ref=pstree.cc">fraction of the cost in a fraction of the time</a>. The idea that crypto is slower than current platforms baffles me. It&apos;s an insanely misinformed idea. And that&apos;s even without considering things like L2 and ETH 2.0.</p><h2 id="thats-it-for-today">That&apos;s it for today.</h2>]]></content:encoded></item><item><title><![CDATA[Wtf is Gossip Protocols?]]></title><description><![CDATA[Gossip protocol is a standard protocol for leaderless distributed systems.]]></description><link>https://pstree.cc/wtf-is-gossip/</link><guid isPermaLink="false">5f1c3fa0c90e0f2d118514d2</guid><category><![CDATA[wtf-series]]></category><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Fri, 18 Mar 2022 16:31:00 GMT</pubDate><media:content url="https://pstree.cc/content/images/2020/07/gossio.gif" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2020/07/gossio.gif" alt="Wtf is Gossip Protocols?"><p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p><strong>Disclaimer:</strong> this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><h2 id="motivation">Motivation</h2><p>This post extends on a problem from our <a href="https://pstree.cc/wtf-is-rendezvous-hashing/">previous post</a> about <em>rendezvous hashing</em>, Assume you have a system consisting of a cluster of <strong><em>serving nodes </em></strong>that simply takes a request from a client and routes it to the correct <strong><em>back-end node</em></strong> after altering some aspects of that request. </p><p><em>Using rendezvous hashing gives us a node we should talk to (the top of the list Cn) but it also gives us an ordering for fail-over if the node failed. This is very interesting because it didn&apos;t only solve the load balancing fail-over issue but it also established whats called distributed k-agreement. Imagine a write request coming to the nodes, this write need to be replicated across nodes in some way so if the node that received the write request failed, the client can fail over to the next. In our scenario, if the client and serving nodes share the same H(Sn, X), nodes can decide the order of replication and create a replication chain that follow the same order as how the client would fallback. Assume we have a discovery service that basically just keeps track of all the nodes around, all members can distributively adapt to changes in the nodes structure without having to communicate with the other nodes.</em></p><p>So my previous post covered what the <strong>client</strong> should do if a <strong>serving node</strong> failed and what the <strong>serving nodes</strong> should do if one of them failed. Yet, without a proper way to know serving node failed as soon as it failed, we can arguably imagine the cluster shrinking back into a single node taking all client traffic.</p><blockquote>Think of it this way: All clients will have some ordering of N nodes, N-1 failed and a single working node.</blockquote><p>It seems we need a way for nodes to learn about other nodes state and event and act accordingly. But how can we do that?</p><blockquote>You know the drill. Take a moment before scrolling down.</blockquote><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/story2.jpg" class="kg-image" alt="Wtf is Gossip Protocols?" loading="lazy"><figcaption>Multi-node system</figcaption></figure><h3 id="use-all-the-health-checks-">Use all the health checks!</h3><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/image.png" class="kg-image" alt="Wtf is Gossip Protocols?" loading="lazy"><figcaption>Me overly excited about health checks. Sue me.</figcaption></figure><p>Well, yes and no. Health checking is a very nice feature that allows some node ( <a href="https://buffer.com/resources/inclusive-language-tech/?ref=pstree.cc">supervisor node?</a>) to probe other nodes through network link to make sure those nodes are /healthy/ whatever that means. It can be as simple as pinging a port and see if it responds, or calling an RPC endpoint that does health diagnostics and return results of the node health. sometimes in critical systems, both types of health checks can be mixed, you can have a more frequent but lightweight health check and a less frequent but more involved diagnostics check. It&apos;s usually used in load balancers to decide if a node is healthy enough to send traffic to. What&apos;s different in our case is that we don&apos;t have a supervisor node. All nodes are both normal serving nodes but they are collectively responsible for the overall availability of the system. Additionally, like any distributed system, nodes can lose communication through network partitions (think of network partitions as your phone temporary disconnecting when passing through a tunnel, you know once your out of the tunnel things will get better but for the time being, you are cut off)</p><p>So maybe health checks are not the best way to go. What else can we do here?</p><blockquote>You know the drill. Take a moment before scrolling down.</blockquote><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2022/03/image-5.png" class="kg-image" alt="Wtf is Gossip Protocols?" loading="lazy" width="940" height="450" srcset="https://pstree.cc/content/images/size/w600/2022/03/image-5.png 600w, https://pstree.cc/content/images/2022/03/image-5.png 940w" sizes="(min-width: 720px) 720px"></figure><h3 id="use-all-the-heart-beats-">Use all the heart beats!</h3><p>Let&apos;s try to analyse this idea. All the nodes know about all the other nodes, every N units of time, the node calls all the nodes it knows about and say &quot;hey I&apos;m fine&quot;, to which the nodes respond &quot;Oh, good to know you are fine. I&apos;ll make sure to remember that for the next N units of time&quot;</p><p><br><strong>How can this friendly banter ever break systems?</strong></p><blockquote>You know the drill. Take a moment before scrolling down.</blockquote><p>This can be /okay/ on 3-4 nodes. But consider the amount of CPU bounded work nodes need to do <strong><em>just</em></strong> for health checks, even worse consider the amount of bandwidth these health checks will imply on the network. For N nodes, there will be N&#xB2; messages floating around <em><strong>just </strong></em>for health checks. Furthermore, because CPUs and network links between these nodes are at different loads, this will cause time deviation in the tickers between the nodes and what you&apos;ll end up seeing is a constant surge of health checks coming in at all times. There is more technically involved discussions on why many engineers believe that heart beats are rarely a good choice for health checks but that&apos;s a topic for another time.</p><h2 id="so-what-do-we-do-then">So, what do we do then?</h2><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2022/03/gossio.gif" class="kg-image" alt="Wtf is Gossip Protocols?" loading="lazy" width="640" height="413"></figure><p>Gossip protocol is a standard protocol for leaderless distributed systems. Many distributed systems rely heavily on Gossip protocol for failure detection and message broadcasting. It follows a very simple model. Imagine you are in your cubicle in an office and you just heard some bad news about a colleague K who got fired (unhealthy node). You, being an active person in the office gossip culture, want to spread that news but immediately realize it&apos;s very inefficient going to every single person telling them what you know (heart beats) and it&apos;s also inefficient to wait for people to come to your desk (health checks) so you decide to let the folks around you about the news. You rely on the social contract that those nodes are equally active in the office gossip culture and will spread this message across the office like an infection. now everyone knows that K got fired and they won&apos;t share data with them (replication) and won&apos;t ask them to deliver on their tasks (serving traffic). Well this is a fun analogy but it doesn&apos;t cover all of the core concepts of gossip so let&apos;s dive in:</p><h3 id="continuous-communication"><br>Continuous communication</h3><p>Gossip relies on the idea that communication is continuous and periodic. You don&apos;t just talk to Lisa when someone is getting fired, you talk periodically about everything that&apos;s happening in the office so that Lisa knows you are okay. If Lisa doesn&apos;t hear from you for a while and <em>no one else is mentioning they saw you in the office,</em> Lisa will assume you are on leave or might&apos;ve gotten fired yourself.</p><p>Each node maintains a state of propagated news. The state can include, list of nodes I heard from in the last N time units (heard from means either they talked to me directly, or someone who talked to me have them in their tracked list) as well as some diagnostic data that we won&apos;t cover here.</p><h3 id="neighboring-v-random">Neighboring v. Random</h3><p>One of the decisions engineers make when implementing gossip is how to pick the nodes for next step of gossip. This can be either a random peer selection or a more deterministic neighboring peer selection. Imagine you have some gossip you want to share, you have two options: either share with neighboring cubicles, those are folks you know for quite sometime and you probably have a closer bond. You can rely on their availability more than others (less probability of a network partition) and it makes the gossip spread more predictably (if all nodes picked the two most neighboring nodes, you can simulate a gossip graph deterministically)</p><p>The other option is to select nodes randomly from all the nodes in the cluster. One of the arguments for that approach is that it increases the chance of a faster spread across different network links. Imagine you have multiple availability zones, if you go with neighboring peer selection, gossip will only hop to availability zone B after everyone in availability zone A learned the news. That&apos;s not optimal for disaster recovery. even worse, imagine the delay between the gossip originating in availability zone A to be picked up by nodes in availability zone C.</p><p>I&apos;ve seen implementations of a hybrid approach where a middleman determines whether this piece of news should be propagated randomly or to neighboring nodes based on the news content. Of course, this adds complexity to an already complex protocol as well as a round trip latency. One approach is to only do the round trip when in doubt. i.e: if all good, use neighboring, if there is a disaster, call the service to do a more informed peer selection.</p><h3 id="networking-protocol">Networking Protocol</h3><p>While usually this protocol is implemented in higher communication stacks, due to the nature of drop resilient communication and low message overhead, sometimes they are implemented in more efficient communication protocols i.e multicast for a much lower overhead on the network and of course less guarantees on delivery.</p><p>Because every node only calls a subset k of the nodes with gossip (usually 2). The gossip will propagate through the cluster in Log&#x2082;N time.</p><h2 id="disadvantages-of-using-gossip-protocols">Disadvantages of using Gossip Protocols</h2><ul><li>Standard implementations of Gossip protocols rely heavily on the idea that nodes are not malicious. If you opt in for a standard implementation, this means one of the nodes clusters can abuse the system if it was breached by hackers. Security-aware Gossip protocol implementations trade off simplicity and overall latency for a more secure approach.</li><li>Standard implementations of Gossip protocols have weak ordering guarantees, which means, due to latency and uneven load distribution among other things, your system can be prune to having two <em>(or more)</em> views of the worlds simultaneously. This is known as &quot;split brain&quot; problem. As long as implementation have guarantees for eventual consistency and the system is designed to tolerate eventual consistency this should be fine but it adds multiple considerations when extending the system.</li></ul><h2 id="who-uses-gossip">Who uses Gossip?</h2><p>Gossip is being used by a large number of distributed systems. Cassandra, Consul, CockroachDB, DynamoDB among the most well know. Also most blockchain-based projects rely on gossip protocols to broadcast new <em><strong>gossip</strong></em> to participating nodes in the peer network.</p><h2 id="further-readings">Further readings</h2><ul><li>SWIM</li><li>Gossip seed nodes</li><li>Gossip Topology-aware peer selection</li><li>Modeling gossip fan out configuration</li><li>Pull-based Gossip</li><li>HashiCorp memberlist</li></ul>]]></content:encoded></item><item><title><![CDATA[Simple problems at scale: log tailing]]></title><description><![CDATA[<p><strong>Simple problems at scale</strong> is a series of mini-blogs that takes trivial-looking problems and discusses how hard these problems can become with larger-scale systems. We are going to start with log tailing. Let&apos;s define some concepts first.</p><h3 id="wtf-are-logs">Wtf are <code>logs</code>?</h3><p>Even though it looks like something very easy</p>]]></description><link>https://pstree.cc/problems-at-scale-log-tailing/</link><guid isPermaLink="false">5d9a25058e6a0945d6837ead</guid><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Wed, 17 Mar 2021 13:25:15 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/10/logs.png" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/10/logs.png" alt="Simple problems at scale: log tailing"><p><strong>Simple problems at scale</strong> is a series of mini-blogs that takes trivial-looking problems and discusses how hard these problems can become with larger-scale systems. We are going to start with log tailing. Let&apos;s define some concepts first.</p><h3 id="wtf-are-logs">Wtf are <code>logs</code>?</h3><p>Even though it looks like something very easy to define, it&apos;s not that simple. For the sake of this article we will treat logs as a series of events stored sequentially on a storage medium. Events can be anything: network requests, sensor readings, GPS coordinates of a moving object, series of interactions with a mobile phone etc. <strong><em>In the very core of the definition of logs, data is immutable. It&apos;s written only once.</em></strong> In the simplest cases logs are printed out of your console program. If you graduated college and this is a program that will run for more than 1 hour, it&apos;s a good idea to have these logs appended to a file.</p><h3 id="now-what-is-log-tailing-exactly">Now what is <code>log tailing</code> exactly?</h3><p>Given the previous definition of logs, we can deduce that <strong><em>most</em></strong> of the time we are actually interested in the most recent results of the data. And even in cases where you are interested in some data in the past, you often express that data in a function of the present. You are interested in data in the logs that are either &quot;Now&quot;, &quot;Recent&quot; or &quot;3 days ago&quot;. This all mean there is much more interest in the <code>tail</code> of the log data rather than any other part. The process of log tailing is to fetch the last N events/lines/transactions in a log.</p><blockquote>An angry commenter will now yawn and say &quot;Why not just use <code>$ tail</code>&quot;?</blockquote><h3 id="how-difficult-is-log-tailing">How difficult is log tailing?</h3><p>The very quick answer is, it depends. It depends on the scale of the logs, how they are arranged and how N is a factor in that.</p><p>But let&apos;s not get ahead of ourselves. Let&apos;s discuss how we would tail logs as they grow starting from your console screen.</p><p>1- Logs are emitted to your console screen<br>It&apos;s simple. You wrote a cool game and you are logging changes happening in UI. You can already see the <code>tail</code> of the logs very clearly. Duh!</p><p>2- Web server serving few hundred active users per day<br>Unix provides a great tool for log tailing from files. type <code>tail /var/www/log0.txt</code> and you&apos;ll have the last 10 lines of that file printed to your console. Assuming your pet photos website got featured on a local lifestyle blog and it&apos;s peaking with 10-100s of requests per second, you&apos;d want to see that action without typing tail 10s of times. Option <code>-f</code> or follow will continuously print out newer logs to your screen. Easy right?</p><p>3- You&apos;ve hit your first million users with around 500 QPS<br>You posted an awesome picture of a cool cat and your website got <a href="https://www.youtube.com/watch?v=QH2-TGUlwu4&amp;ref=pstree.cc">really famous</a>. Now looking at logs is a little problematic because you need a way to debug an issue happening in production. Neither <code>tail</code> nor <code>tail -f</code> can help you because of the overwhelming number of requests. Files are getting bigger and they need to be <code>rotated</code></p><blockquote>Log rotation: A process of isolating, archiving and compressing old logs.</blockquote><h3 id="logs-apocalypse-you-have-multi-million-user-base-with-500kqps-">Logs apocalypse: you have multi-million user base with &gt;500kQPS.</h3><p>Here is where everything bends. Your web server is not a single ssh-able machine. Your log is not a single file. Answering the question that UNIX <code>tail</code> used to answer &quot;What are the last N events in my log?&quot; is not easy anymore. It&apos;s also time to be skeptical and ask questions like &quot;What do we really need from all those logs?&quot; and &quot;How are we going to use the data?&quot; These lazy-sounding questions are actually very pro-active and lead to insight on how to tackle scale problems that come with that amount of throughput. </p><p>Now that you have gigabytes (or petabytes, hypothetical traffic is free anyway) of log entries coming in every second, your logs are being distributed across 10s or 100s of machines. You want an optimised system for writing these logs with guarantees on ordering and most importantly consistency. The system must be able to tail logs from hundreds of machines (while maintaining order) efficiently. <a href="https://kafka.apache.org/documentation/?ref=pstree.cc">Kafka</a> and <a href="https://engineering.fb.com/core-data/logdevice-a-distributed-data-store-for-logs/?ref=pstree.cc">LogDevice</a> are two open-source examples of distributed data stores for logs that are built with the principle of <strong><em>immutable writes and tailing</em></strong> in mind.</p><h2 id="what-s-next">What&apos;s next?</h2><p>Go through docs for <a href="https://kafka.apache.org/documentation/?ref=pstree.cc">Kafka</a> and <a href="https://engineering.fb.com/core-data/logdevice-a-distributed-data-store-for-logs/?ref=pstree.cc">LogDevice</a> to learn about distributed logging. Spin up a local Kafka cluster. I find the <a href="https://github.com/spotify/docker-kafka?ref=pstree.cc">Spotify docker image </a>the fastest way to spin up Kafka locally and <a href="https://media1.popsugar-assets.com/files/thumbor/eOF2Umn-mqNGnohxrtjeurwWDmI/fit-in/2048xorig/filters:format_auto-!!-:strip_icc-!!-/2018/08/20/677/n/1922283/1118a12c5b7adb1e342de9.55515725_/i/Michael-Scott-Misquotations-Office-Video.jpg?ref=pstree.cc">play with it</a>.</p>]]></content:encoded></item><item><title><![CDATA[Wtf is rendezvous hashing?]]></title><description><![CDATA[Distributed Systems WTF Series]]></description><link>https://pstree.cc/wtf-is-rendezvous-hashing/</link><guid isPermaLink="false">5e2e317ac90e0f2d118513fb</guid><category><![CDATA[tech]]></category><category><![CDATA[wtf-series]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Mon, 08 Jun 2020 16:03:39 GMT</pubDate><media:content url="https://pstree.cc/content/images/2020/06/hash.png" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2020/06/hash.png" alt="Wtf is rendezvous hashing?"><p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p><strong>Disclaimer:</strong> this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><h2 id="motivation">Motivation</h2><p>Let&apos;s start by proposing a problem. Assume you have a system consisting of a <strong><em>serving node </em></strong>that simply takes a request from a client and routes it to the correct <strong><em>back-end node</em></strong> after altering some aspects of that request.</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/story1.jpg" class="kg-image" alt="Wtf is rendezvous hashing?" loading="lazy"><figcaption>A single node system</figcaption></figure><p>First thing you notice that serving node can be a bottleneck if not scaled proportionately to the traffic hitting it. We&apos;ll probably need a <strong><em>multi-node serving system. </em></strong>How can we route requests to a cluster of nodes?</p><blockquote>Take a moment here and think of potential solutions before scrolling.</blockquote><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/story2.jpg" class="kg-image" alt="Wtf is rendezvous hashing?" loading="lazy"><figcaption>Multi-node system</figcaption></figure><h3 id="use-all-the-load-balancers-">Use all the load balancers!</h3><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/image.png" class="kg-image" alt="Wtf is rendezvous hashing?" loading="lazy"><figcaption>Me overly excited about load-balancers</figcaption></figure><p>Well, maybe. Load balancing is a very good technique to scale up systems. But let&apos;s take a deeper look at what that load balancer would look like. Would the load balancer be a single node serving a multi-node system? It seems like load-balancing might be the answer but we&apos;ll need more than just a single node load balancing.</p><h3 id="client-based-load-balancing">Client-based load balancing</h3><p>That&apos;s a good idea. Clients are by nature scaled up to the traffic <strong><em>(they are the traffic)</em></strong>. Let&apos;s make the client aware of all the serving nodes and let it decide which node to talk to based on some semantics of the client. Let&apos;s create a <strong><em>smart client </em></strong>that can hash a request and get a serving node.</p><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2020/06/story3.jpg" class="kg-image" alt="Wtf is rendezvous hashing?" loading="lazy"><figcaption>smart-client</figcaption></figure><p>That&apos;s great. We have a client that can know which node to call directly depending on that client&apos;s identity. Assuming uniform load between all clients, this should be a good solution.</p><p>But what if the client-assigned <em>serving node</em> crashed?</p><blockquote>Take a moment here and think of potential solutions before scrolling.</blockquote><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2020/06/story4.jpg" class="kg-image" alt="Wtf is rendezvous hashing?" loading="lazy"></figure><h2 id="can-we-do-better"><a href="http://timroughgarden.org/?ref=pstree.cc">Can we do better?</a></h2><p>In traditional hashing you give a <em>one-way</em> method input X (<strong><em>client-id</em></strong> in our example) and it returns H(X) result (<em><strong>serving node address</strong></em> in our example). This is a widely used concept and part of almost all programming languages in a way or another. The shortcoming of that in our example happens when H(X) points to a failing node. This is problematic because the client doesn&apos;t know any extra information to fall back to. This is where <em><strong>rendezvous hashing </strong></em>shines. Instead of<strong><em> hashing</em></strong> single input single output, <em><strong>rendezvous hashing</strong></em> takes the form <code>H(Sn, X) = Cn</code><br>Where <strong><em>Sn</em></strong> is set of elements (<strong><em>serving nodes</em></strong> in our example), <strong><em>X</em></strong> is the input for hashing (<strong><em>client-id</em></strong> in our example) and returns <strong><em>Cn</em></strong> an ordering of <em><strong>Sn</strong></em> weighted with a complete scoring (think of it as confidence values adding to 1).</p><blockquote>Take a moment here and think &#xA0;how this form can be useful in our example.</blockquote><p>Using <em><strong>rendezvous hashing </strong></em>gives us a node we should talk to (the top of the list <strong><em>Cn</em></strong>) but it also gives us an ordering for fail-over if the node failed. This is very interesting because it didn&apos;t only solve the load balancing fail-over issue but it also established whats called <strong><em>distributed k-agreement. </em></strong>Imagine a write request coming to the nodes, this write need to be replicated across nodes in some way so if the node that received the write request failed, the client can fail over to the next. In our scenario, if the client and serving nodes share the same H(Sn, X), nodes can decide the order of replication and create a replication chain that follow the same order as how the client would fallback. Assume we have a discovery service that basically just keeps track of all the nodes around, all members can distributively adapt to changes in the nodes structure without having to communicate with the other nodes.</p>]]></content:encoded></item><item><title><![CDATA[wtf series - what the fuzz?]]></title><description><![CDATA[<p>Fuzzing is a software black-box testing technique where units of a software system are being continuously tested against a stream of random data. Units can be methods, API endpoints, Database interfaces, etc. The software unit is then monitored for exceptions such as crashes, or potential memory leaks.</p><h2 id="why-the-fuzz">Why the fuzz?</h2>]]></description><link>https://pstree.cc/wtf-series-what-the-fuzz/</link><guid isPermaLink="false">5dcdb028c90e0f2d11851315</guid><category><![CDATA[tech]]></category><category><![CDATA[wtf-series]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Sun, 26 Jan 2020 16:50:42 GMT</pubDate><media:content url="https://pstree.cc/content/images/2020/01/segv.jpeg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2020/01/segv.jpeg" alt="wtf series - what the fuzz?"><p>Fuzzing is a software black-box testing technique where units of a software system are being continuously tested against a stream of random data. Units can be methods, API endpoints, Database interfaces, etc. The software unit is then monitored for exceptions such as crashes, or potential memory leaks.</p><h2 id="why-the-fuzz">Why the fuzz?</h2><p>The main objective of fuzzing is to get the application to crash. It&apos;s not meant to test any business bound logic. </p><p>Fuzzers work best for discovering vulnerabilities that can be exploited by buffer overflow, DOS, cross-site scripting and SQL injection. These schemes are often used by malicious hackers intent on wreaking the greatest possible amount of havoc in the least possible time. Fuzz testing is less effective for dealing with errors that does not crash the software.</p><p>Fuzzing often reveals serious defects within the software and that are usually overlooked by engineers. When you fuzz test a unit of your software you expose it to <em><strong>&quot;unbiased&quot;</strong></em> input that is not affected by assumptions developers usually assume. Teams maintaining large scale projects, where these crashes are really costly, run fuzz tests continuously either as a qualifier for release or even continuously run against HEAD of code-under-test independent from release process with proper reporting when a crash happen.</p><p>There are a few variations of fuzzing-oriented instrumentation techniques available and usually it&apos;s recommended to test your software against few of them. The most popular techniques are:</p><ul><li>Address sanitization (detects addressability issues)</li><li>Leak sanitization (detects memory leaks)</li><li>Thread sanitization (detects data races and deadlocks)</li><li>Memory sanitization (detects use of uninitialized memory)</li></ul><h2 id="how-do-fuzzers-work">How do fuzzers work?</h2><p>Before going over how fuzzers work, let&apos;s start with defining <em><strong>seed data</strong></em> as a corpus of data that represents the skeletal structure of data. Fuzzers rely on seed corpus to derive new inputs to test the software against. While fuzzers usually don&apos;t need seed corpus and can run without them, good seed helps in providing a range of possible skeletal structures to enable fuzzers to work more efficiently and achieve coverage faster especially when the structure of the data is complicated i.e a complex JSON object or a deeply nested protocol buffer.</p><p>Fuzzing engines offer different interfaces depending on the language. <a href="https://github.com/google/gofuzz?ref=pstree.cc">gofuzzer</a> for example, offers an extensive interface for generating random structures. It lets developers decide how to perform the fuzzing.</p><p>For example, this snippet uses gofuzzer to generate an object with randomized values of internal values.</p><pre><code>type MyType struct {
    A string
    B string
    C int
    D struct {
    	E float64
    }
}

f := fuzz.New()
object := MyType{}
f.fuzz(&amp;object)</code></pre><p> It lets you decide your fuzzing logic on your own. For example you can use the previous snippet to fuzz a method against 1000 random inputs.</p><pre><code>for i := 0; i &lt; 1000; i++ {
	f.Fuzz(&amp;object)
	FuncToTest(object) # test FuncToTest against 1000 random inputs
}</code></pre><p>Other fuzzers like LLVM libfuzzer for C/C++ provide a method interface that is feeded random data, software units are called inside this method with passed data to test against fuzz. The following is an example from the official <a href="https://llvm.org/docs/LibFuzzer.html?ref=pstree.cc">documentation</a> for libfuzzer. This fails if fuzzer engine passes <code>HI!</code> in <code>data</code> .</p><pre><code>extern &quot;C&quot; int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
  if (size &gt; 0 &amp;&amp; data[0] == &apos;H&apos;)
    if (size &gt; 1 &amp;&amp; data[1] == &apos;I&apos;)
       if (size &gt; 2 &amp;&amp; data[2] == &apos;!&apos;)
       __builtin_trap();
  return 0;
}</code></pre><p> As per the docs, if you tried running this using: <code>clang -fsanitize=address,fuzzer file_name.cc &amp;&amp; ./a.out</code> will catch this and crash very quickly. This showcases how powerful fuzzers are in catching even this specific corner case. You can use the method <code>LLVMFuzzerTestOneInput</code> to test your code-under-test by calling the method inside it.</p><pre><code>extern &quot;C&quot; int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
  FuncToTest(Data, Size);
  return 0;
}</code></pre><p>BONUS: check <a href="https://github.com/google/fuzzing/blob/master/tutorial/libFuzzerTutorial.md?ref=pstree.cc">this tutorial</a> on how to reproduce heartbleed vulnerability in OpenSSLv1.0.1 using libFuzzer</p><h2 id="resources">Resources</h2><p><a href="https://llvm.org/docs/LibFuzzer.html?ref=pstree.cc">LLVM libFuzzer</a></p><p><a href="https://github.com/google/fuzzing/blob/master/tutorial/libFuzzerTutorial.md?ref=pstree.cc">Google LibFuzzer Tutorial</a></p><p><a href="https://github.com/google/gofuzz?ref=pstree.cc">Google gofuzzer</a></p>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is Linux namespaces?]]></title><description><![CDATA[<p>Let&apos;s start by running <code>man namespaces</code> </p><p></p><blockquote>Name:<br>namespaces - overview of Linux namespaces</blockquote><blockquote>Description:<br>A namespace wraps a global system resource in an abstraction that makes it appear to the processes within the<br>namespace that they have their own isolated instance of the global resource. &#xA0;Changes to</blockquote>]]></description><link>https://pstree.cc/wtf-series-wtf-is-linux-namespaces/</link><guid isPermaLink="false">5c2c581f8e6a0945d6837b8d</guid><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Fri, 02 Aug 2019 14:06:04 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/07/yeah-1.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/07/yeah-1.jpg" alt="wtf series - wtf is Linux namespaces?"><p>Let&apos;s start by running <code>man namespaces</code> </p><p></p><blockquote>Name:<br>namespaces - overview of Linux namespaces</blockquote><blockquote>Description:<br>A namespace wraps a global system resource in an abstraction that makes it appear to the processes within the<br>namespace that they have their own isolated instance of the global resource. &#xA0;Changes to the global &#xA0;resource<br>are &#xA0;visible to other processes that are members of the namespace, but are invisible to other processes. &#xA0;One use of namespaces is to implement containers.</blockquote><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2019/04/tenor.gif" class="kg-image" alt="wtf series - wtf is Linux namespaces?" loading="lazy"><figcaption>Realizing I&apos;m over using this one</figcaption></figure><h2 id="so-wtf-is-namespaces">So Wtf is namespaces?</h2><p>Namespaces (<em><strong>ns</strong></em> for short) is a Linux kernel feature that allows creating a logical view of system resources that&apos;s different from the physical resources a system has. This is the core idea of <strong><em>Containers </em></strong>like<strong><em> </em></strong><em>docker, rkt and LXC.</em></p><p>A simple idea of how Namespaces work can be derived backward from it&apos;s applications. Let&apos;s take a docker container that runs a <strong><em>Nodejs</em></strong> server. If you do <code>docker exec -it &lt;container name&gt; /bin/bash</code> and then <code>ps aux</code> you&apos;ll find processes running into container having PIDs 1,2,3. Which usually collides with running <code>ps aux</code> on your terminal. This is possible because of one of Linux namespaces, the PID namespace. It isolates the process ID number space. This means two processes on the same host can have the same PID if they are on different PID namespaces.</p><p><em>This concept of resource isolation is really important in containers. Imagine running two containers on a host machine without this isolation. ContainerA could simply </em><code>kill -9 $PID</code> from ContainerB or <code>unmount</code> a disk that ContainerC depends on. BONUS: MNT namespace.</p><p>It&apos;s worth nothing that namespaces don&apos;t limit resource usage. It controls visibility of resources between processes. BONUS#2: <a href="https://pstree.cc/what-the-heck-are-linux-cgroups/">Wtf is cgroups?</a></p><h2 id="7-namespaces-of-ice-and-fire">7 namespaces of Ice and Fire</h2><figure class="kg-card kg-image-card kg-card-hascaption"><img src="https://pstree.cc/content/images/2019/07/yeah.jpg" class="kg-image" alt="wtf series - wtf is Linux namespaces?" loading="lazy"><figcaption>I feel bad explaining my word play with images.</figcaption></figure><ol><li>MNT - isolate filesystem mount points</li><li>UTS - isolate hostname and domainname</li><li>IPC - isolate interprocess communication (IPC) resources</li><li>PID - isolate the PID number space</li><li>NET - isolate network interfaces</li><li>USR - isolate UID/GID number spaces</li><li>Cgroup - isolate cgroup root directory</li></ol>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is chroot?]]></title><description><![CDATA[<p>Let&apos;s starting by typing <code>man chroot</code> in a linux terminal and see what we get</p><!--kg-card-begin: markdown--><blockquote>
<p><em>Name:</em><br>
<em>chroot - run command or interactive shell with special root directory.</em><br>
<em>Usage:</em><br>
<em><code>chroot [OPTION] NEWROOT [COMMAND [ARG]...]</code></em><br>
~ <em>Linux manual</em></p>
</blockquote>
<!--kg-card-end: markdown--><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2019/04/tenor.gif" class="kg-image" alt loading="lazy"></figure><h3 id="so-what-really-is-chroot">So what really is chroot?</h3><p>Chroot is a unix command that changes the</p>]]></description><link>https://pstree.cc/wtf-is-chroot/</link><guid isPermaLink="false">5c2c58368e6a0945d6837b91</guid><category><![CDATA[tech]]></category><category><![CDATA[wtf-series]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Sun, 28 Apr 2019 04:24:51 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/04/bandersnatch-800x445.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/04/bandersnatch-800x445.jpg" alt="wtf series - wtf is chroot?"><p>Let&apos;s starting by typing <code>man chroot</code> in a linux terminal and see what we get</p><!--kg-card-begin: markdown--><blockquote>
<p><em>Name:</em><br>
<em>chroot - run command or interactive shell with special root directory.</em><br>
<em>Usage:</em><br>
<em><code>chroot [OPTION] NEWROOT [COMMAND [ARG]...]</code></em><br>
~ <em>Linux manual</em></p>
</blockquote>
<!--kg-card-end: markdown--><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2019/04/tenor.gif" class="kg-image" alt="wtf series - wtf is chroot?" loading="lazy"></figure><h3 id="so-what-really-is-chroot">So what really is chroot?</h3><p>Chroot is a unix command that changes the root directory of COMMAND to NEWROOT specified in parameters. A very simple use case is: <code>chroot ~/Downloads ls -la</code></p><p>Looking at the previous command and the definition of chroot one would say that this command will:<br>1- change root to Downloads, cd to Downloads<br>2- run <code>ls -la</code> inside Downloads and print out Downloads directory content</p><p>While this thinking process is correct, this command will actually fail for two reasons. The first reason this command will fail is because chroot needs root access and will fail without root permissions. <em>If this didn&apos;t happen to you then you probably copy pasted a command from the internet that you don&apos;t understand and ran it with root permissions and if I were you I would spend sometime thinking about my life choices.</em><br>The second reason, after fixing the root permissions, is that the shell won&apos;t be able to execute <code>ls -la</code> in the new root directory because it won&apos;t find it under <code>/bin/ls</code> and this demonstrates a powerful feature of chroot. Chroot does more than a simple cd into a directory. Chroot changes what <code>/</code> means for the running process. In our example the shell will look for <code>ls</code> in ~/Downloads/bin/ instead of / because chroot changed the root to be under Downloads directory.<br>Let&apos;s try this one more time but after making <code>ls</code> available in the new root.</p><pre><code>mkdir -p ~/Downloads/bin/
cp /bin/ls /Downloads/bin


// make sure to make all dependencies available too
// for simplicity, will make all shared libs available but for better context use `ldd` to get dependencies of a specific command.
sudo cp -a /usr ~/Downloads
sudo cp -a /lib ~/Downloads
sudo cp -a /lib64 ~/Downloads



sudo chroot ~/Downloads ls -la</code></pre><p>Now that we made <code>ls</code> available to the new root living in <code>~/Downloads/bin/ls</code>, command will output the content of Downloads directory.<br><br>You might have noticed that <code>COMMAND</code> argument is optional in chroot. By default, chroot runs <code>$SHELL</code> in the new root which will also fail if you don&apos;t have the shell executable available under <code>NEWROOT</code>.</p><h2 id="but-why">But why?</h2><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2019/04/WhyWouldYouDoThat.gif" class="kg-image" alt="wtf series - wtf is chroot?" loading="lazy"></figure><p><strong><strong>Testing and development</strong></strong>: A test environment can be set up in chroot for software that would otherwise be too risky to deploy on a production system.</p><p><strong><strong>Dependency control</strong></strong>: Software can be developed, built and tested in a chroot populated only with its expected dependencies. This can prevent some kinds of linkage skew that can result from developers building projects with different sets of program libraries installed.</p><p><strong><strong>Compatibility</strong></strong>: Legacy software or software using a different ABI must sometimes be run in a chroot because their supporting libraries or data files may otherwise clash in name or linkage with those of the host system.</p><p><strong><strong>Recovery</strong></strong>: Should a system be rendered unbootable, a chroot can be used to move back into the damaged environment after bootstrapping from an alternate root file system (such as from installation media, or a Live CD).<br><br>Worth noting: if the topic got your interest and you went to search for more content about the topic you might find people refering to chroot as <code>chroot jail</code> and this is slightly incorrect because chroot can&apos;t be used as a security measure. It <em>simulates</em> a separate environment but a process that knows it&apos;s running under a chroot environment can <em>escape</em> the environment.</p><h2 id="sources">Sources</h2><p>Wikipedia<br>Linux Man<br>My terminal?</p>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is protobuf?]]></title><description><![CDATA[<p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>Protocol buffers are</p>]]></description><link>https://pstree.cc/wtf-is-protobuf/</link><guid isPermaLink="false">5c2cd7e98e6a0945d6837be2</guid><category><![CDATA[wtf-series]]></category><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Wed, 27 Feb 2019 13:19:45 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/02/protocolbuffers.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/02/protocolbuffers.jpg" alt="wtf series - wtf is protobuf?"><p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>Protocol buffers are Google&apos;s language-neutral, platform-neutral, extensible mechanism for serializing structured data &#x2013; think XML, but smaller, faster, and simpler. You define how you want your data to be structured once, then you can use special generated source code to easily write and read your structured data to and from a variety of data streams and using a variety of languages. [<a href="https://developers.google.com/protocol-buffers/?ref=pstree.cc#what-are-protocol-buffers">src</a>]</p><h2 id="history">History</h2><p><strong>XML</strong><br>One of the oldest data serialization standards driven from the SGML, the Standard Generalized Markup Language. Standardized 1996~1998, XML was the primary structured and semi-structured data serialization standard and the basis for SOAP protocol. It&apos;s human-readable, structured and very verbose. [<a href="https://www.w3schools.com/xml/?ref=pstree.cc">snippet src</a>]</p><pre><code>&lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&gt;
&lt;breakfast_menu&gt;
&lt;food&gt;
    &lt;name&gt;Belgian Waffles&lt;/name&gt;
    &lt;price&gt;$5.95&lt;/price&gt;
    &lt;description&gt;
   Two of our famous Belgian Waffles with plenty of real maple syrup
   &lt;/description&gt;
    &lt;calories&gt;650&lt;/calories&gt;
&lt;/food&gt;
&lt;food&gt;
    &lt;name&gt;Strawberry Belgian Waffles&lt;/name&gt;
    &lt;price&gt;$7.95&lt;/price&gt;
    &lt;description&gt;
    Light Belgian waffles covered with strawberries and whipped cream
    &lt;/description&gt;
    &lt;calories&gt;900&lt;/calories&gt;
&lt;/food&gt;
&lt;food&gt;
    &lt;name&gt;Berry-Berry Belgian Waffles&lt;/name&gt;
    &lt;price&gt;$8.95&lt;/price&gt;
    &lt;description&gt;
    Belgian waffles covered with assorted fresh berries and whipped cream
    &lt;/description&gt;
    &lt;calories&gt;900&lt;/calories&gt;
&lt;/food&gt;
&lt;food&gt;
    &lt;name&gt;French Toast&lt;/name&gt;
    &lt;price&gt;$4.50&lt;/price&gt;
    &lt;description&gt;
    Thick slices made from our homemade sourdough bread
    &lt;/description&gt;
    &lt;calories&gt;600&lt;/calories&gt;
&lt;/food&gt;
&lt;food&gt;
    &lt;name&gt;Homestyle Breakfast&lt;/name&gt;
    &lt;price&gt;$6.95&lt;/price&gt;
    &lt;description&gt;
    Two eggs, bacon or sausage, toast, and our ever-popular hash browns
    &lt;/description&gt;
    &lt;calories&gt;950&lt;/calories&gt;
&lt;/food&gt;
&lt;/breakfast_menu&gt;</code></pre><p><strong>JSON</strong><br>Short for <strong><em>JavaScript Object Notation</em></strong>, popularized around early 2000s was a step forward for data representation and serialization as it was less verbose than XML, easier to support on browsers, faster to process and it enforces consistent structure. This made it the main data serialization standard for the modern web for long years.</p><pre><code>// simple representation of a breakfast menu with only one item
[
  {
    &quot;name&quot;: &quot;Homestyle Breakfast&quot;,
    &quot;price&quot;: &quot;$6.95&quot;,
    &quot;description&quot;: &quot;Two eggs, bacon or sausage, toast, and our ever-opular hash browns&quot;,
    &quot;calories&quot;: 950
  }
]</code></pre><h2 id="protocol-buffers-protobuf-">Protocol buffers (protobuf)</h2><p>Google developed Protocol Buffers for use in their internal services. It is a <em><strong>binary</strong></em> encoding format that allows you to specify a <em><em><strong>schema</strong></em></em> for your data using a specification language, like so:</p><pre><code>message Person {
  required string name = 1;
  required int32 id = 2;
  optional string email = 3;
}

</code></pre><p>The Protocol Buffers specification is implemented in various languages: Java, C, Go, etc. are all supported, and most modern languages have an implementation. Here is a Java example using the previous schema:</p><pre><code>Person john = Person.newBuilder()
    .setId(1234)
    .setName(&quot;John Doe&quot;)
    .setEmail(&quot;jdoe@example.com&quot;)
    .build();
output = new FileOutputStream(args[0]);
john.writeTo(output);</code></pre><pre><code>Person john;
fstream input(argv[1],
    ios::in | ios::binary);
john.ParseFromIstream(&amp;input);
id = john.id();
name = john.name();
email = john.email();</code></pre><p>Using protocol buffers has many advantages over plain text serializations like JSON and XML:</p><ul><li>Very dense data which result in very small output and therefore less network overhead</li><li>Declared schema makes parsing from most languages very straightforward with less boilerplate parsing code</li><li>Very fast processing</li><li>Binary encoded and hard to decode without knowledge of the schema</li><li>Backward compatibility as a side-effect</li></ul><h2 id="references">References</h2><p><a href="https://developers.google.com/protocol-buffers/?ref=pstree.cc#what-are-protocol-buffers">Google developers - Protocol Buffers</a></p>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is pstree?]]></title><description><![CDATA[<p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>I wrote this</p>]]></description><link>https://pstree.cc/wtf-is-pstree/</link><guid isPermaLink="false">5c4b86e48e6a0945d6837d45</guid><category><![CDATA[wtf-series]]></category><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Sun, 24 Feb 2019 22:29:27 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/01/Pstree_freebsd.png" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/01/Pstree_freebsd.png" alt="wtf series - wtf is pstree?"><p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>I wrote this mini-blog because of the many people who asked me what does the name of the blog mean. I was surprised because it&apos;s something I use on a daily basis and I just assumed every programmer will know it.</p><p><code>pstree</code> is a unix command-line tool that prints tree of processes. Unlike <code>ps</code>, it prints the hierarchy of processes and not only list the processes. If you specify a username as an argument, it trims out any process not owned by that user. The result is usually a list of subtrees of the original tree.</p><h2 id="but-what-can-it-do">But, what can it do?</h2><p>let&apos;s start with the syntax</p><pre><code>pstree [-a, --arguments] [-c, --compact] 
       [-h, --highlight-all, -Hpid, --high&#x2010;light-pid pid] [-g] --show-pgids] 
       [-l, --long] [-n, --numeric-sort] [-p, --show-pids] [-s, --show-parents] 
       [-u, --uid-changes] [-Z, --security-context] 
       [-A, --ascii, -G, --vt100, -U, --unicode] [pid, user]</code></pre><p>if you do <code>man pstree</code> in your terminal you will find the previous snippet and guide for all the basic functionality of <code>pstree</code> so I&apos;ll skip all that and go to a very specific use case where you can benefit from it</p><h3 id="-1-you-are-building-a-program-that-forks-processes-for-specific-purpose-and-kill-them-afterwards-you-want-to-debug-the-scenarios-and-see-if-the-forked-processes-life-cycle-is-handled-correctly">#1: You are building a program that forks processes for specific purpose and kill them afterwards. You want to debug the scenarios and see if the forked processes life-cycle is handled correctly</h3><blockquote>&quot;Meh. You can always use <code>ps</code>&quot; ~ angry commenter</blockquote><p>Using <code>pstree</code> you can view the process hierarchy and check that it&apos;s deleted correctly without leaving zombie children processes. This is a very common pitfall when you try to fork a process from your main program and then kill it later. Most languages use a basic <code>SIGKILL</code> and in many cases the spawned process dies leaving out orphan processes often called <code>zombie processes</code><br><br>A <em>very simple</em> way for debugging these scenarios is using <code>pstree</code> and <code>grep</code> on the process name during your program execution to make sure the process lifecycle is handled correctly. One way to ensure killing processes correctly is to use <code>setgid</code> and kill the process group containing the forked process and any children processes.</p><h2 id="references"><strong>References</strong></h2><p><a href="http://man7.org/linux/man-pages/man1/pstree.1.html?ref=pstree.cc">Man pstree(1)</a></p>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is a goroutine?]]></title><description><![CDATA[<p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>Before explaining what</p>]]></description><link>https://pstree.cc/wtf-is-goroutines/</link><guid isPermaLink="false">5c2c0aa88e6a0945d6837b3d</guid><category><![CDATA[tech]]></category><category><![CDATA[wtf-series]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Sun, 20 Jan 2019 19:03:58 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/01/gophercomplex5_0.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/01/gophercomplex5_0.jpg" alt="wtf series - wtf is a goroutine?"><p>This is part of a series of posts explaining cryptic tech terms in an introductory way.</p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><p>Before explaining what goroutines are, let&apos;s define some concepts first</p><p><strong>Concurrency: </strong>The ability for different parts of a computer program to execute in out-of-order or in partial order without affecting the end result of that program. <strong>Concurrency is not parallelism.</strong></p><p><strong>Parallelism: </strong>The <em>simultaneous</em> execution of different parts of a computer program across a number of cores improving overall performance. <strong>Concurrency is about <em>dealing with</em> lots of things at once. Parallelism is about <em>doing</em> lots of things at once.</strong></p><h2 id="goroutines">Goroutines</h2><p>Goroutines are a way of doing tasks <em>concurrently</em> in golang. They allow us to create and run multiple methods or functions concurrently in the same address space inexpensively. They are lightweight abstractions over threads because their creation and destruction are very cheap as compared to threads, and they are scheduled over OS threads. Executing the methods in the background is as easy as prepending the word <code>go</code> in a function call. Golang achieves parallelism by multiplexing goroutines onto multiple OS threads so if one should block, such as while waiting for I/O, others continue to run. Their design hides many of the complexities of thread creation and management and delegates that to the go runtime scheduler.</p><p>There is a number of differences between goroutines and native threads:</p><ul><li>Memory Consumption: Goroutines don&apos;t require much space (~2kb of stack space) as they grow by allocating memory from the heap space. Threads are greedy they need ~1MB of memory and a guard page which you can think of like a wall between threads memory pools</li><li>Setup/Teardown: Greedy threads cost significantly more during setup/teardown as they request resources from OS and have to free those after they finish executing. Because goroutines are created and terminated by the runtime, they are very cheap to create and destroy.</li><li>Context Switching: When a thread block, on I/O for example, another thread has to take it&apos;s place. This operation is called context switching and during the context switching the OS has to save the thread state which is ALL the registers (ballpark ~40)[don&apos;t know an exact number, don&apos;t hesitate to message me if you have a more accurate number], program counter, stack pointer and co-processor state. Goroutines are scheduled cooperatively and when a switch occurs, only 3 registers need to be saved/restored - Program Counter, Stack Pointer and Data registers(DX). The cost is much lower.</li><li>Goroutines have channels and wait groups, primitive structures for communication. One google search will let you know how much harder doing that in native threads is.</li></ul><h2 id="quick-hands-on-fetch-json-from-a-list-of-urls-in-goroutines-and-only-output-the-result-when-all-the-goroutines-are-finished">Quick Hands-on: Fetch json from a list of urls in goroutines and only output the result when all the goroutines are finished</h2><p><strong>// not recommended, just here to demonstrate how channels work and for the sake of completeness. </strong><br><strong>Channels version:</strong></p><pre><code>func main() {
  urls = string[]{
    &quot;url1&quot;,
    &quot;url2&quot;,
    ...
  }
  done := make(chan bool) // We don&apos;t need any data to be passed
  responses := make(chan string) // save responses coming from urls

  for _, url := range urls {
      go func(url) {
          responses &lt;- fetchUrls(url)
          done &lt;- true // signal that the routine has completed
      }(url)
  }

  // Since we started len(urls) routines, receive len(urls) messages.
  // this will block main routine til all are recieved
  for i := 0; i &lt; len(urls); i++ {
      &lt;- done
  }
    
  for i := range responses { // treating the channel as a range
      fmt.Println(i)
  }
}</code></pre><p><strong>Waitgroups version: </strong></p><pre><code>func main() {
  urls = string[]{
    &quot;url1&quot;,
    &quot;url2&quot;,
    ...
  }
  responses := make(chan string) // save responses coming from urls
  var wg sync.WaitGroup
  wg.Add(len(urls)) // increment the counter of the waitgroup by len(urls)

  for _, url := range urls {
      go func(url string) {
          defer wg.Done() // defer keyword execute the given method after the scope is terminated, wg.Done() decrements the counter of the waitgroup
          responses &lt;- fetchUrl(url)
      }(url)
  }

  go func() {
    for response := range responses { // treating the channel as a range
      fmt.Println(response)
    }
  }

  wg.Wait() // blocks til the counter reaches zero
}</code></pre><h2 id="what-s-next">What&apos;s next?</h2><p>Keywords: <br>buffered vs unbuffered channels, reusing golang waitgroups, non-blocking channel operations, channel timeouts, worker pools, ticker, mutexes, atomic counters, user space threads vs kernel threads.</p><h2 id="references">References</h2><p><a href="https://www.youtube.com/watch?v=cN_DpYBzKso&amp;ref=pstree.cc">Rob Pike - Concurrency is not parallelism </a></p><p><a href="https://golang.org/doc/effective_go.html?ref=pstree.cc#goroutines">Effective Go - Goroutines</a></p><p><a href="https://gobyexample.com/?ref=pstree.cc">Go by example</a></p>]]></content:encoded></item><item><title><![CDATA[wtf series - wtf is cgroups?]]></title><description><![CDATA[<p>This is the first of a series of posts explaining cryptic tech terms in an introductory way. </p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><h2 id="cgroups">Cgroups</h2><p>Cgroups,</p>]]></description><link>https://pstree.cc/what-the-heck-are-linux-cgroups/</link><guid isPermaLink="false">5c29ecef8e6a0945d6837b38</guid><category><![CDATA[tech]]></category><category><![CDATA[wtf-series]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Wed, 09 Jan 2019 09:59:22 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/01/1.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2019/01/1.jpg" alt="wtf series - wtf is cgroups?"><p>This is the first of a series of posts explaining cryptic tech terms in an introductory way. </p><p>Disclaimer: this series is not intended to be a main learning source. However, there might be follow up posts with hands-on experiments or deeper technical content for some of these topics.</p><h2 id="cgroups">Cgroups</h2><p>Cgroups, or control groups, are <strong>Linux</strong> kernel features that provide mechanisms allowing processes to be organized into hierarchical groups whose usage of various types of resources ( ram, cpu, disk i/o, network i/o ) can then be limited and monitored. There are two major versions of cgroups with some differences in groups&apos; hierarchies and the fact that multiple cgroups per process is not supported in cgroupsv2 unlike cgroupsv1. We will be discussing only cgroupsv2 here with little references to v1.</p><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2019/01/cgroups.png" class="kg-image" alt="wtf series - wtf is cgroups?" loading="lazy"></figure><p>Cgroups configuration structure usually looks like this<br>* <em>assuming it&apos;s mounted at /sys/fs/cgroup/</em></p><!--kg-card-begin: markdown--><pre><code>/sys/fs/cgroup/
            cgroup1/
                cgroup3/
            cgroup2/
                cgroup4/
</code></pre>
<!--kg-card-end: markdown--><p>This means rules/limits assigned to cgroups1 affects both cgroups1 processes and the processes of children cgroups of cgroups1, cgroups3 in this example. </p><p>It should be noted that not all cgroup controllers are available in the v2 yet as it was only marked available in kernel version 4.5. &#xA0;Currently, <code>memory</code>, <code>io</code>, <code>rdma</code>, <code>pids</code>, <code>perf_event</code> and <code>cpu</code> controllers are available.</p><h2 id="example-use-cases">Example use cases</h2><p>-	Limiting network access for a process so that it can&apos;t connect to network. <strong><em>net_io</em></strong> <br>-	Prioritizing disk I/O from high priority processes like database servers and/or static servers. <strong><em>blkio in cgroupsv1 io in cgroupsv2</em></strong><br>-	Apply inbound/outbound network firewalls to a certain cgroup. <strong><em>net_cls in cgroupsv1 and xt_cgroup iptable filter in cgroupsv2</em></strong><br>-	Prioritizing outgoing network traffic for web crawlers and content aggregator processes. <strong><em>net_prio and xt_cgroup iptable filter in cgroupsv2</em></strong><br>-	Monitor CPU usage of all sideloaded tools. <strong><em>cpu_acct</em></strong></p><h2 id="quick-hands-on-setting-network-i-o-priority-higher-for-mysqldb-server">Quick hands-on: Setting network I/O priority higher for MySQLdb server</h2><h3 id="setting-up-cgroups">Setting up cgroups</h3><p>Install <code>libcgroup2</code> package on your distro. It can take different names in different distributions.</p><p>Mount cgroup2 to /cgroups</p><pre><code>$ mount -t cgroup2 nodev /cgroups</code></pre><h3 id="creating-cgroups">Creating cgroups</h3><pre><code>$ mkdir /cgroup2/highiopriority
</code></pre><p>This creates a cgroup called <code>highiopriority</code>. Now we want to add <code>io</code> to <code>cgroup.subtree_control</code> to be able to use its controller.</p><pre><code>$ echo &quot;+io&quot; &gt; /cgroups/cgroup.subtree_control
</code></pre><p>Now if we printed <code>cgroup.controller</code> file for the <code>highiopriority</code> cgroup, we should find <code>io</code> enabled.</p><!--kg-card-begin: markdown--><pre><code>$ cat /cgroups/highiopriority/cgroup.controllers
io
</code></pre>
<!--kg-card-end: markdown--><p>Now we can change <code>io.weight [10,1000]</code> to give our new cgroup higher io priority than default value <code>100</code> by adding the new weight to <code>/cgroups/highiopriority/io.weight</code></p><p><code>echo &quot;1000&quot; &gt; io.weight</code></p><h3 id="assigning-processes-to-cgroups">Assigning processes to cgroups</h3><p>Now that we have a cgroup with high io priority, the only missing thing is adding processes to this cgroup. To do so, we should add pids of the processes we want to prioritize their io, mysqldb server in our case, to cgroup.procs file in the cgroup directory. </p><p><code>cat /var/lib/mysql/{yourservername}.pid &gt; /cgroups/highiopriority/cgroup.procs</code></p><p>Now we have mysql io prioritized over default cgroup. There are so many interesting things you can do with cgroups on your own workstation. <em>My recommendation is:</em> try to extend this tutorial with limiting your default browser RAM usage and instead of figuring out the pid this old fashioned way, search of a way on how you can auto capture an executable pid and assign it to a certain cgroup on the fly.</p><h2 id="what-s-next">What&apos;s next</h2><p>The next couple of topics I have in the queue are all Linux, Golang and some networks. I&apos;m also planning to work on a mini-docker project implementing some of linux concepts that I will be explained in the coming topics to build a mini-docker engine and experiment with different kernel features. Please feel free to post suggestions and feedback here <em><em><em><em><a href="https://curiouscat.me/essamhassan?ref=pstree.cc">https://curiouscat.me/essamhassan</a></em></em></em></em></p><h2 id="further-readings-">Further readings:</h2><p><a href="http://man7.org/linux/man-pages/man7/cgroups.7.html?ref=pstree.cc">http://man7.org/linux/man-pages/man7/cgroups.7.html</a></p><p><a href="https://www.kernel.org/doc/Documentation/cgroup-v1/?ref=pstree.cc">https://www.kernel.org/doc/Documentation/cgroup-v1/</a></p><p><a href="https://www.kernel.org/doc/Documentation/cgroup-v2.txt?ref=pstree.cc">https://www.kernel.org/doc/Documentation/cgroup-v2.txt</a></p>]]></content:encoded></item><item><title><![CDATA[A practical guide for evaluating software engineering job offers]]></title><description><![CDATA[<h3 id="you-go-with-the-biggest-pay-cheque-it-s-that-simple-right-wrong-">You go with the biggest pay cheque. It&apos;s that simple, right? Wrong. </h3><p>Don&apos;t get me wrong, your salary is very important and you should never compromise on that. However, I believe that not spending enough time on your job decisions directly affects your overall job satisfaction</p>]]></description><link>https://pstree.cc/a-practical-guide-for-evaluating-software-engineering-job-offers/</link><guid isPermaLink="false">5c1aca3f8e6a0945d6837915</guid><category><![CDATA[careers in tech]]></category><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Thu, 27 Dec 2018 14:44:37 GMT</pubDate><media:content url="https://pstree.cc/content/images/2019/01/money-1.jpg" medium="image"/><content:encoded><![CDATA[<h3 id="you-go-with-the-biggest-pay-cheque-it-s-that-simple-right-wrong-">You go with the biggest pay cheque. It&apos;s that simple, right? Wrong. </h3><img src="https://pstree.cc/content/images/2019/01/money-1.jpg" alt="A practical guide for evaluating software engineering job offers"><p>Don&apos;t get me wrong, your salary is very important and you should never compromise on that. However, I believe that not spending enough time on your job decisions directly affects your overall job satisfaction when your job stops meeting your inflated optimistic expectations. I&apos;ll try to walk through all the details that matter to me when I&apos;m evaluating job offers. In some sections you&apos;ll find a &quot;no-no&quot; list, which is basically the list of things I believe are a hard pass <em><strong>for me</strong></em> if any company had them. Please remember that this is how <em><strong>I</strong></em> approach the topic and it&apos;s not necessarily the best approach. Before going into details, let&apos;s go through some quick FAQs around the topic.</p><p><strong>1- Do I really have to go through your boring post even though I only have one offer?</strong><br>A little offended but Ok. YES, you should. You have to know what you are walking into even if it&apos;s your only offer to adjust your expectations to reality. Or even better, walk away from an offer that will harm your career and be worse than a few extra months of job hunting.<br><br><strong>2- Does that guide apply to everyone and every company? </strong><br>These points are deliberately generalized to be a fits-all model and of course any kind of generalization have flaws. So, read with caution that your country, company, offer, etc might not match 100% of the criteria but still be good enough. For example, not all companies offer equity, but that doesn&apos;t mean that companies that does not are worse. You have to put in mind the market in that country, other compensation factors, your skillset, etc and make a mindful choice.<br><br><strong>3- What are the numbers beside some sub categories?</strong><br>These are weights that sum up to 10 per category. A category with less than 7 points is a bad indicator. One with less than 4 is <em>ehrab ya yaseen.</em></p><p><br><strong><strong>Whether it is a feedback, question or if you feel something is missing or wrong: </strong></strong><em><em><a href="https://curiouscat.me/essamhassan?ref=pstree.cc">https://curiouscat.me/essamhassan</a></em> </em>and I&apos;ll consider adding it here.</p><h2 id="company">Company</h2><p><strong>Upper Management [3]</strong><br>You should learn about the management strategy and goals. How are there actions conforming with their promises and claimed visions. Good signs are long consistent leadership with little conflicts and a series of delivered promises. Bad signs are inflated executive salaries, unpredictable reorgs, insider trading gossip, record of ethical or legal misconduct. <br>	My no-no list:<br>		- Companies with history of unpredictable layoffs of large number of employees. Yes, you Uber. Reference: <a href="https://bit.ly/2CuTD26?ref=pstree.cc">https://bit.ly/2CuTD26</a><br>		- Companies with irresponsible or corrupt Management. Uber, again but now Tesla too. References (just a few..): <a href="https://bit.ly/2Q0Fb5s?ref=pstree.cc">https://bit.ly/2Q0Fb5s</a> <a href="https://nyp.st/2ShFvyT?ref=pstree.cc">https://nyp.st/2ShFvyT</a> <a href="https://bit.ly/2MZqwuZ?ref=pstree.cc">https://bit.ly/2MZqwuZ</a> </p><p><strong>Performance [3]</strong><br>By performance, I mean both stock value performance and financial performance for non-IPO companies. Look at their numbers and see if they maintain consistent good performance. You don&apos;t have to be an analyst to do that. I like this guide as it&apos;s simple, and they don&apos;t use lots of cryptic financial terms: <a href="https://bit.ly/2T2nvbA?ref=pstree.cc">https://bit.ly/2T2nvbA</a></p><p><br><strong>Culture [4]</strong><br>This is a very hard topic to tackle, because for big companies it&apos;s almost always depending on where you work in these companies. And in startups it&apos;s not easier at all. Because startups mature at a much faster rate than big companies, startups&apos; cultures can change in months, even weeks from the heaven workplace to a terrible place to work or vice versa. You have to be able to find your type. Not all people like relaxed cultures and relaxed goals. Some people want something fast and high velocity. Others want something formal and strict ( which is not necessarily a bad thing ). So the first step in this point is to find what your type is. If you look at the feedbacks on Glassdoor you&apos;d be surprised of the people who left your dream companies because they weren&apos;t &apos;serious enough&apos; or that they weren&apos;t working on challenging enough projects or just the fact that people didn&apos;t get any work done.<br><br>	My no-no list:<br>		- Companies with toxic blame culture, where you&apos;ll be afraid to make a mistake in your code and this fear will end up crippling you and make it harder for you to make impact and grow in the company.<br>		- Companies with no well-defined cultures. Those who let mid-level managers drive the culture of the company and not the opposite. It takes one bad manager for the company to sink into toxicity losing most of their talent and gaining a very bad reputation for it. Most engineers with a couple years of experience will be able to relate to this specific type.</p><h2 id="career">Career</h2><p><strong>Role [3]</strong><br>Is it really what you want to do? Look at the description and communicate efficiently with your prospect manager. Don&apos;t &quot;figure it out on the spot&quot;. Recruiters usually <em>sell</em> to you that you can move teams if you didn&apos;t like your first team. This is true, but not the complete truth. Yes, you can, but doing that very early is a serious bad sign on your profile. The outcome can range from a very bad feedback stuck to your profile with this company forever to an immediate firing decision.</p><p><strong>Manager [4]</strong><br>YES, your next manager should be one of the most important factors in your decision making process. Not only in this category but overall. Your first manager will help you navigate your future in a company, prep you for your role and communicate their feedback clearly with you. It&apos;s very tricky to get insights about your manager but you can do so by either asking fellows in that teams, if possible, or having calls with them asking them questions that can reveal as much as possible about their management style. <a href="https://www.joelonsoftware.com/2000/08/09/the-joel-test-12-steps-to-better-code/?ref=pstree.cc">The Joel Test</a> is one of the very insightful list of questions to start that conversation with. <a href="https://blog.codinghorror.com/the-programmers-bill-of-rights/?ref=pstree.cc">The programmer&apos;s bill of rights</a> is less appropriate for a manager call but very good for your online research of the company.<br><br>	My no-no list:<br>		- Passive aggressive managers.<br>		- Technically incompetent managers.<br>		- &#xA0;Unethical managers.<br>		- &#xA0;Managers who have conflict of interest with your career growth*** This is very important. Say you are going to work for a company and the manager said something like &quot;we need someone to maintain our legacy system, because it&apos;s in a bad shape, and we have been searching for someone to maintain it for a year now&quot;. Now, the phrase means a couple of things. First, it&apos;s a legacy system, there will be no updates to it or feature changes. This means no challenges and therefore halted promos. Also, It&apos;s against the manager&apos;s interest for you to switch to something else. It&apos;s a plus negative sign if the stack they are using for the legacy system is a popular stack &quot;Java&quot; it basically means no one wanted the job.</p><p><strong>Growth [3]</strong><br>It&apos;s really hard to measure your growth in a company before joining but you can still rely on a couple of factors. One of the things to consider, most good companies have a well defined criteria for promotions in the form of a job ladder guide. It&apos;s usually well-defined making it highly unlikely for you to be denied a promotion if you are meeting the publicly shared guide. Ask your recruiter/manager about your potential for promotions.</p><p>But again, promotions are not the only kind of growth you get in a company. Skills growth is a very important factor. Learn how the company invests in you and your skills.<br><br>	My no-no list:<br>		- Companies with vague unclear selective promotions.<br>		- Companies with low demand in upper levels. It&apos;s usually much harder to get promoted or even get the chance to work on challenging exciting projects if they have an influx of senior engineers. And even though you&apos;ll be surrounded with senior engineers, and you&apos;ll be able to learn from them, I believe the cons outweigh the pros.</p><h2 id="contract">Contract</h2><p><em>Beware: too many underlined words for very valid reasons ahead.</em></p><p>There are a couple of points you should check while reading any offer letter. Aside from the basics like checking the title, role, salary, bonus, etc, you should read clauses about working hours, holidays and sick leaves, causes of termination, start/end dates and notice period.</p><p><em>The most important thing in this section is to check for any restrictive clauses. Things like non-compete, non-solicitation, non-dealing, non-poaching, no-second-job, etc. These can have serious implications on your future and you should make sure you are okay with whatever is in your contract, otherwise revise it with your recruiter.</em></p><p>My no-no list:<br><em>		- Very restrictive clauses like long non-compete especially if it might conflict with my future interest.</em></p><h2 id="compensation">Compensation</h2><p><em>Sub-categories in italic are optional*</em></p><p><strong>Base: cash you get every month in the bank and <em>usually</em> presented in yearly format.</strong><br>Base is always within a fixed range per level. You should research your company and country compensation average and most importantly the average skills in that specific level. Compare your research output with your offer and you&apos;ll end up with a clear idea if you are getting paid enough. Another important tip if you are moving to a new country/state, most countries tax people differently based on <strong><em>many factors.</em></strong> Make sure you learn your net salary and how it compares to the cost of living of your new city, if you are moving.</p><p>My no-no list:<br>		- Offers with very low bases in exchange of &quot;a chance to learn&quot;. This usually happens with startups with tight budget and high potential. The rule is if you are going to do the work, you have to be paid the money.</p><p><strong><em>Stocks: company stock grants to employee usually distributed over four years.</em></strong><br>Those are optional and most companies don&apos;t offer them, <em><strong>BUT </strong></em>you should expect your offer to include stocks/stock options, if the company is an early to mid stage startup. Stocks are usually a standard part of job offers from companies like Amazon, Google, Facebook and Apple. It&apos;s a way of retaining talent as you <em>usually</em> receive them over four years. The vesting schedule, which is the schedule for you to receive your shares, is usually a standard 25/25/25/25. However, It still differs from a company to another. Amazon, for example, offers a different 5/15/20/40. Schedules have more details than that so you should be aware of the plan you are on and make sure you are ok with it. Also, stocks are usually a very good negotiation point, unlike base, and you can always try to push for 20-30% if you think you deserve it.</p><p><strong><em>Signing Bonus: one time bonus you get when you join the company.</em></strong><br>Optional signing bonus is usually given for candidates as a standard offering or to make the offer more competitive compared to other offers. A good strategy to evaluate the signing bonus is to divide it on 4 years and add to your total compensation. We&apos;ll talk more about that at the end of this section.</p><p><strong><em>Yearly Bonus: % of your base salary given out yearly on a prorated basis.</em></strong><br>Bonuses are pretty standard. Worth noting that most companies have a performance multiplier which means if you are initially offered 15% bonus, your final bonus can be between 1 x 15% to 2 x 15%. Of course these numbers are not accurate and will differ depending on the company. Feel free to ask your recruiter about these numbers.</p><p><strong>Yearly Raise: % increase of your base salary usually based on performance.</strong><br>This is pretty standard as well but usually not clear enough on your package. You should ask about the raise and make sure it&apos;s within the acceptable ranges. I&apos;ve had encounters with companies that offer very low yearly raise so unless you promote, your salary won&apos;t be really changed. Make sure you are ok with your yearly raise.</p><p><em><strong>Refreshers:</strong></em><br>The word refreshers usually means additional stocks given out after your initial stocks. Not all companies have refreshers and companies have different schedules and reasons for giving refreshers. Know if your potential employer offers any kind of stock refreshers and when those refreshers are given.</p><p><strong>Benefits: </strong><br>Yes, benefits are not just perks. They directly translate to your compensation. A company that offers free food adds a surplus of money not spent on food to your base. A company supporting your transportation ticket adds that amount of money on your base as well. Make sure to have this input very clear to you when you are making a decision. Also, be critical about these benefits. A company can offer 20+ benefits on their site but all can end up a very small surplus to your income and that you&apos;d have been better going with the company with the higher base fulfilling the Tom Cruise dream.</p><p><strong>Total compensation: </strong>It gets really overwhelming boiling down all these in your salary so I have this formula that can help you do it. And since this is specifically for software engineers:</p><figure class="kg-card kg-image-card"><img src="https://pstree.cc/content/images/2018/12/download.jpeg" class="kg-image" alt="A practical guide for evaluating software engineering job offers" loading="lazy"></figure><figure class="kg-card kg-image-card kg-width-wide kg-card-hascaption"><img src="https://pstree.cc/content/images/2018/12/render--1-.png" class="kg-image" alt="A practical guide for evaluating software engineering job offers" loading="lazy"><figcaption>* expected years at that company, ** costIdx is cost index of the country you are moving to [optional], *** yearly.bonus.percent not raise</figcaption></figure><p>Keep in mind that this is a made up formula put together by a very sleepy person late in the night, and it&apos;s a little different to the well-known total compensation calculations on the internet so treat it with a grain of salt.</p><h2 id="at-the-end"><strong>At the end</strong></h2><p>Take your time, consider everything in this post but most importantly consider what matters to you before making up your mind. Good luck!</p><p></p><!--kg-card-begin: html--><iframe src="https://docs.google.com/forms/d/e/1FAIpQLScGv-b6tRTZZLIdDbQdGaCxIBW1F_j8X-TAgAlQKiHfXJe88Q/viewform?embedded=true" width="640" height="576" frameborder="0" marginheight="0" marginwidth="0">Loading...</iframe><!--kg-card-end: html-->]]></content:encoded></item><item><title><![CDATA[15 pieces of advice I wish I had been given before graduating computer science]]></title><description><![CDATA[<p><strong><strong><em>I&#x2019;m not sure if I&#x2019;m even qualified to give advices but lets say these are based on my top mistakes</em></strong></strong></p><p>1- Be open to learning everything even the tools and technologies you don&#x2019;t like.</p><p>2- The best way to learn a new thing is</p>]]></description><link>https://pstree.cc/pieces-of-advice-i-wish-i-had-been-given-before-graduating-computer-science/</link><guid isPermaLink="false">5c1ac2738e6a0945d6837908</guid><category><![CDATA[tech]]></category><category><![CDATA[life]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Wed, 19 Dec 2018 22:17:21 GMT</pubDate><media:content url="https://pstree.cc/content/images/2018/12/cvr.jpg" medium="image"/><content:encoded><![CDATA[<img src="https://pstree.cc/content/images/2018/12/cvr.jpg" alt="15 pieces of advice I wish I had been given before graduating computer science"><p><strong><strong><em>I&#x2019;m not sure if I&#x2019;m even qualified to give advices but lets say these are based on my top mistakes</em></strong></strong></p><p>1- Be open to learning everything even the tools and technologies you don&#x2019;t like.</p><p>2- The best way to learn a new thing is to use it.</p><p>3- Learn as many languages as you want BUT always have this one language you excel at. And by excel at I mean a language your googling/typing ratio with it is 1 Search / 100 LOC or less</p><p>4- Read books and fat references. Get the concrete big picture and not only the &#x201C;Up and Running&#x201D; version</p><p>5- Invest alot of time planning for your first job.</p><p>6- Ask for feedback frequently and use those feedbacks</p><p>7- Learn about the market needs</p><p>8- Take good care of your resume. Develop it iteratively and take industry feedback whenever you can</p><p>9- Algorithms and Data Structures is 50% boost in your career and sometimes more. So Practice, practice, practice</p><p>10- Work life balance is not a choice. By overworking you are not necessarily over achieving</p><p>11- Avoid Imposters and beware of falling into the dunning kruger effect. Always remember, you are not there yet.</p><p>12- Ask others about how they achieved what they achieved. Get insights from your peers and ask for feedback.</p><p>13- Networking and maintaining good work relations are not luxuries. Career is not only about being a good coder.</p><p>14- Maintain a Trello board (or basically any other board) of your plans and achievements. Monitor your performance</p><p>15- Eat healthy and workout. Your health is important not only for your productivity but also for your overall happiness. Nobody wants to spend the day at hospitals</p>]]></content:encoded></item><item><title><![CDATA[The unusual guide for cracking interviews at Google, Facebook, Amazon, Cloudflare, Bloomberg and others]]></title><description><![CDATA[<h2 id="introduction">Introduction</h2><p>This guide is intended for people pursuing software engineering careers in high-end tech companies. I will be discussing my encounters with these companies in a number of verticals: <em>Resumes</em>, <em>Preparations</em> and <em>Interviews. </em><strong>I&apos;ll try to make this post as beneficial as possible and not yet another &quot;</strong></p>]]></description><link>https://pstree.cc/the-unusual-way-for-cracking-interviews/</link><guid isPermaLink="false">5c10b1d86417050c48f01263</guid><category><![CDATA[careers in tech]]></category><category><![CDATA[tech]]></category><dc:creator><![CDATA[Essam Hassan]]></dc:creator><pubDate>Sun, 16 Dec 2018 11:42:42 GMT</pubDate><media:content url="https://pstree.cc/content/images/2018/12/cvr1.1-1.jpg" medium="image"/><content:encoded><![CDATA[<h2 id="introduction">Introduction</h2><img src="https://pstree.cc/content/images/2018/12/cvr1.1-1.jpg" alt="The unusual guide for cracking interviews at Google, Facebook, Amazon, Cloudflare, Bloomberg and others"><p>This guide is intended for people pursuing software engineering careers in high-end tech companies. I will be discussing my encounters with these companies in a number of verticals: <em>Resumes</em>, <em>Preparations</em> and <em>Interviews. </em><strong>I&apos;ll try to make this post as beneficial as possible and not yet another &quot;binge on problems&quot; advice. Feel free to ask/message me about anything. Whether it is a feedback, question or if you feel something is missing or wrong: </strong><em><a href="https://curiouscat.me/essamhassan?ref=pstree.cc">https://curiouscat.me/essamhassan</a></em></p><h2 id="resumes">Resumes</h2><p>Many people believe that passing the interview is the hardest part. But if you looked into the numbers, passing the screening phase is much more problematic as many factors contribute to your odds that are irrelevant to your experience and technical expertise. i.e referrals, resume format, average level of other candidate at the time of screening, hiring season, etc.</p><p>In this section I like to divide these companies into two categories, even though there will still be variance between companies in the same category. The first category is companies hiring for specific roles in specific teams. They look for highly specialised people. In my case, this was with <strong>Cloudflare</strong>. One of my favourite interview processes. The Title was Distributed Systems Engineer - Data Pipelines Infrastructure. The process was all specific around this title and the team I&apos;ll be potentially joining. More to that in the next section.<br>		<em>How to pass their screening? </em>Customise your resume to show off your most relevant experiences to what they need. In my case, they wanted someone with Kafka and Elasticsearch knowledge and I happened to work and interacted with both on a relatively advanced level @Instabug so I mentioned it in my resume. Add the most relevant experiences but also remember not to exaggerate or &apos;oversell&apos; yourself because you&apos;ll be expected to meet the resume expectations in the interviews.</p><p>The second category is for companies that hire pre-allocation. This means you get hired then find a team to get matched with. This is usually the case with Facebook, Google, Amazon and Bloomberg. In Google and Amazon, you get matched after passing all the interviews. With Facebook and Bloomberg they even go further and make the matching after your orientation/training. <br>		<em>How to pass their screening?</em> In this category, hiring is usually focused on high level technical skills. They are looking for someone who 1- had past technical impact on his team, 2- demonstrates problem solving skills on abstract levels. Because <strong><em>most</em></strong> of the time, they don&apos;t know where you&apos;ll end up working and they want you to have skills that are as generic as possible. Mentioning that you are a Laravel expert won&apos;t be really attractive. On the other hand, mentioning that you wrote multiple services with multiple languages will definitely help. This shows you are language agnostic and that you, to a certain degree, have good design skills. Also these companies rely heavily on referrals. Try to get a referral from your network and don&apos;t be shy to reach out to older colleagues or 2nd degree friends. If they think you are good it&apos;s in their benefit to refer you as they get referral bonus for every passing candidate they refer.</p><h2 id="preparation">Preparation</h2><p>The same categories that reflect on resumes do reflect on your preparation afterward. When a Google recruiter think that your resume looks good and demonstrate good generic problem solving and design skills, your interviews performance should reflect those skills. So for these companies ( Amazon, Bloomberg, Google, Facebook ) I&apos;d recommend working on those two aspects.</p><p><em>1- Generic problem solving skills</em><br>	You are expected to be able to tackle medium-hard programming problems very fast in your preferred language. and to make sure your solution is correct by testing it. Usually you are put into this test multiple times with multiple conditions. i.e IDE, Phone, Chromebook, Whiteboard. My recommendations are <br>			- Practice on tackling the problems you are not familiar with not just memorising solutions and pattern matching. In my Google interview which was my last, I solved problems from all the popular books and was done with leetcode and yet all the problems were new to me. So I wouldn&apos;t advice memorising problems. You should be able to tackle problems you&apos;ve not seen before.<br>			- Learn your language very well. Some interviewers might tolerate lack of language knowledge but you can&apos;t bet your luck on that.<br>			- Book recommendations: Cracking the Coding interview of course is one of the good books to prepare from but the problems in there are relatively easier than Google and Facebook level, make sure you don&apos;t limit yourself to that difficulty. Also don&apos;t miss out on the soft skill advices mentioned on how to tackle interviews situations. Elements of programming interviews is also a very nice book with richer technical content but it&apos;s only focus on technical questions.<br>			- In these books you&apos;ll find them mentioning baseline skills that every candidate should be familiar with. Be <em>really </em>comfortable implementing and using all of these data structures and algorithms. Many problems are usually a twist on a well known algorithm or data structure and usually interviewers expect you not to struggle implementing the basic idea.</p><p><br><em>2- Design skills</em><br>	These skills are usually tested by two types of questions. Either you&apos;ll be asked to design a separate system with certain requirement. You should expect follow up questions changing the requirements and should design the system to be flexible on changing requirements. The other type of questions comes in the format of a follow up question for a problem solving question. Expect questions like &quot;How to scale that solution if we have 1000x input&quot; or &quot;How to shard this&quot;. You should be familiar with concepts like sharding, load balancing, inverse indices, replication, etc. If you have industry experience with large scale systems you should not find an issue with their questions but if you are not, your best bet is reading Grokking the system design interview and other design books to understand distributed systems basics.</p><p><em>3- Role specific skills</em><br>	For companies hiring for role specific skills, in My case this happened with Cloudflare (Data Pipelines Infra) and HelloFresh (Golang). Your preparation should be derived from 1- Job description 2- Recruiter Call. As as many questions about the role requirement and what they do. In my case, Cloudflare was looking for someone with advanced Unix experience, deep Kafka understanding, Elasticsearch internals. These are the information I asked about in the recruiter call. You should always ask about what they do and what problems they have. This will reflect on what they are looking in an Engineer. In Cloudflare I asked about &quot;How they use Elasticsearch&quot; and it turned out they don&apos;t. They wanted someone familiar with the internals of elasticsearch as they have similar infrastructure. </p><p>With HelloFresh it was different, they were interested in someone with good Golang experience. I wouldn&apos;t have known that as their interview offered Javascript, PHP and Go as options even though they were looking specifically for Go experts. Asking questions in early phases will let you know what they are exactly looking for. Keep in mind that recruiters are your advocates. It&apos;s in their interest for you to succeed and pass the interviews and they can help you better understand the requirements.<br></p><h2 id="interviews">Interviews</h2><p><em>1- Amazon</em><br>I interviewed with Amazon twice. In the first time I passed the phone interview and then they delayed the process due to headcount. So I had to do the process again and did another phone interview and 5 rounds of onsite interviews. Both phone interviews and 4 out of 5 of the onsite interviews were the same format. The interviewer starts by giving you a vague problem for you to solve and then 20 mins behavioural interview focused on Amazon leadership principles <a href="https://www.amazon.jobs/en/principles?ref=pstree.cc">https://www.amazon.jobs/en/principles</a><br><br>There was one interview that was slightly different. It was focused on Object Oriented Design ( Not distributed systems ) and the requirements got incrementally tougher as we went through the design. It&apos;s good to start with a design that you can extend later and make room for flexibility in your designs.<br><br>	How to prepare? Problem solving, Amazon leadership principles, Object Oriented Design.<br>	What they focus on? leadership skills, ability to communicate solutions clearly</p><p><em>2- Bloomberg</em><br>Bloomberg had one of the longest interviews I&apos;ve ever had. All technical interviews followed the same format. 1-2 problem solving questions. Except my first interviewer asked a little bit about my background but I felt it was a warm up question not really contributing to the process. If you find the problem too easy, finish your solution quickly because there will probably be another one.<br>	How to prepare? Problem solving<br>	What they focus on? -</p><p><em>3- Cloudflare</em><br>Cloudflare interviews were my favourite. The first round was a Hacker Rank screening task followed by a screening phone call. The screening phone call was an interesting conversation about scalability and <em>&quot;all role related&quot;. </em>It was a mix between introducing me to the role and figuring out if I can have a good conversation about their infrastructure. The engineer proposed an infrastructure problem that they had and asked me if I have any ideas how this problem can be solved. It was not a question-answer format but rather a water cooler conversation to get a sense of how deep I can go in details about certain topics. The second set of interviews were proposing problems of high scale nature. I can&apos;t disclose the question but they were very different from all the other companies. It combined problem solving with extreme code optimisation. I was allowed to google things and read documentations.<br>	How to prepare? Read the role description carefully, Know what skills they expect and get as much information as possible in the first call. Refresh your memory about the basics of every skill mentioned and make sure you have good command of the language you choose.<br>	What they focus on? High volume network/data, scalability and distributed systems</p><p><em>4- Google</em><br>I had the regular Google process that is well known on the internet with slightly different experience. It started with a recruiter screening call which was <em>&apos;not an interview&apos;</em> but I ended up being asked technical questions about red black trees and golang internals. Then had a phone interview with one moderate problem. After a week I went through a loop of interviews with problems varying in difficulty. Some of the interviews included follow up systems questions in the format of &quot;How to scale this&quot; and &quot;How to shard that&quot;. Google Interview questions were relatively harder than the rest of the interviews.<br>	How to prepare? Expect not known questions. All my questions were new and I&apos;ve never seen before which was surprising given that I solved a relatively big number of problems. Don&apos;t rely on memorising solutions or even pattern matching. Make sure you practise solving new problems. Also questions had twists in the description so pay attention to the description and ask clarifying questions about anything you think is unclear.<br>	What they focus on? The main focus in the interviews was problem solving with interest in scale and low level knowledge.</p><p><em>5- Facebook</em><br>My facebook process was cut short because of headcount issues I had to pause the process. The interviews were similar to Google process without the first screening call. The problems were clearer and a little bit more familiar. I believe they look for the same type of Engineers as Google and preparing for these interviews should be the same.</p><h2 id="conclusion">Conclusion</h2><blockquote>If there&#x2019;s one advice I could give to people, it would be to take action. I think that this is what separates those who get the offers they really want and those who don&#x2019;t. Taking the steps and actually preparing and applying to the companies they want to get in. Many people think it&#x2019;s impossible for them, or that they are not good enough, but this is not true. If you work hard, prepare, apply, and repeat, you are eventually going to get the offers you dream of. - <a href="http://fb.com/mshokry10?ref=pstree.cc">Mahmoud Shokry</a></blockquote><p>I do believe that most of the readers who think they are not good enough for these companies are just overwhelmed with the stigmas caused by media and engineers benefiting from the exclusivity. Take action and know that hard work pays off.</p><h2 id="resources">Resources</h2><p><a href="https://www.amazon.com/Cracking-Coding-Interview-Programming-Questions/dp/0984782850?ref=pstree.cc">Cracking the Coding Interview, 6th Edition</a><br><a href="https://leetcode.com/?ref=pstree.cc">LeetCode.com</a><br><a href="https://www.interviewbit.com/?ref=pstree.cc">InterviewBit.com</a><br><a href="https://www.pramp.com/?ref=pstree.cc">Pramp.com</a><br><a href="https://leetcode.com/mockinterview/?ref=pstree.cc">LeetCode Mock Interviews</a></p><p></p>]]></content:encoded></item></channel></rss>